ole存储 通过流名称可以直接访问该流的数据

是的,在结构化存储(如 OLE 复合文件)中,通过流名称可以直接访问该流的数据。这种设计类似于通过文件名直接访问文件内容,但需注意其底层机制和结构化存储的特性。以下是详细解释:


1. 直接访问的含义

当调用 OpenStream 并指定流名称后:

  • 无需索引或映射:流名称本身就是数据的唯一标识符,不需要通过哈希表、索引键或其他中间结构来定位数据。
  • 直接获取接口指针:成功打开流后,会返回 IStream* 接口指针,通过该指针可直接调用 ReadWriteSeek 等方法操作数据。
// 示例:打开流并读取数据
IStream* pStream = nullptr;
HRESULT hr = lpStorage->OpenStream(L"MyDataStream", ..., &pStream);
if (SUCCEEDED(hr)) {
    BYTE buffer[1024];
    ULONG bytesRead = 0;
    hr = pStream->Read(buffer, sizeof(buffer), &bytesRead);
    // 直接操作数据...
    pStream->Release();
}

2. 结构化存储的底层实现

尽管流名称是直接访问的入口,但结构化存储的实现可能依赖以下机制:

  • 目录表(Directory Entries):复合文件内部维护了一个类似文件系统的目录结构,记录所有流和子存储的名称及其物理位置。
  • 直接定位:打开流时,系统通过名称在目录表中查找对应的元数据,直接定位到流数据的存储位置(类似于文件系统的 inode 查找)。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传


3. 与文件系统的关键区别

虽然流名称的访问方式类似文件名,但结构化存储在以下方面有所不同:

特性文件系统结构化存储
数据存储单元文件(File)流(Stream)
层级结构目录(Directory)和文件存储(Storage)和流
访问粒度文件级(整个文件为单位)流级(可精细控制字节流)
并发控制依赖操作系统文件锁通过 STGM_SHARE_* 标志控制
持久化方式独立文件嵌入复合文件(如 .doc, .xls)

4. 直接访问的限制

流名称的直接访问需满足以下条件:

  • 名称必须存在:流名称需在当前存储中已定义,否则返回错误(如 STG_E_FILENOTFOUND)。
  • 名称唯一性:同一存储下不能有同名的流和子存储。
  • 访问权限匹配:必须以兼容模式打开父存储(例如,若父存储以只读模式打开,则无法通过流写入数据)。

5. 应用场景示例

场景:读取 Word 文档中的嵌入式图片
  1. 打开根存储(Root Storage)。
  2. 通过流名称直接访问文档属性流(如 \x05SummaryInformation)。
  3. 通过子存储名称进入嵌套存储(如 Images 存储)。
  4. 通过流名称直接读取图片数据流(如 Image1.jpg)。
// 伪代码示例:访问嵌套流
IStorage* pRootStorage = ...; // 打开根存储
IStorage* pSubStorage = nullptr;
pRootStorage->OpenStorage(L"Images", ..., &pSubStorage); // 打开子存储

IStream* pImageStream = nullptr;
pSubStorage->OpenStream(L"Image1.jpg", ..., &pImageStream); // 直接访问流
// 读取图片数据...

6. 为什么说这是“直接”访问?

  • 无中间解析层:流名称到数据的映射由结构化存储系统内部管理,开发者无需关心物理存储细节(如数据块的位置、分配策略等)。
  • 接口直接暴露数据流IStream 接口提供类似文件句柄的操作(Read/Write),直接面向字节流。

7. 注意事项

  • 名称大小写敏感:某些结构化存储实现(如 Windows 复合文件)的流名称是大小写敏感的。
  • 保留字符:避免在名称中使用 /\ 等可能被解析为路径分隔符的字符。
  • 性能影响:频繁打开/关闭流可能影响性能,建议缓存常用流的 IStream 指针。

结论

通过流名称可以直接访问结构化存储中的流数据,这种设计结合了文件系统的直观性和结构化存储的封装性。其底层通过目录表实现快速定位,但开发者无需关心物理细节,只需通过名称和标准的 IStream 接口操作数据。这种机制使得结构化存储非常适合管理复杂、嵌套的二进制数据(如 Office 文档)。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

金士顿

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值