gpt4 book ai didi

C++ 如何刷新 std :stringbuf?

转载 作者:行者123 更新时间:2023-11-30 04:01:20 31 4
gpt4 key购买 nike

我需要将进程的标准输出(二进制数据)放入字符串缓冲区并在另一个线程中使用它。

这是制作人:

while (ReadFile(ffmpeg_OUT_Rd, cbBuffer, sizeof(cbBuffer), &byteRead, NULL)){
tByte += byteRead; //total bytes
sb->sputn(cbBuffer, byteRead);
}
m_bIsFinished = true;
printf("%d bytes are generated.\n", tByte);

这是消费者:

while (!PCS_DISPATCHER_INSTANCE->IsFinished())
Sleep(200);
Sleep(5000);
Mystringbuf* sb = PCS_DISPATCHER_INSTANCE->sb;
printf("Avail: %d\n", sb->in_avail());

事实证明,消费者无法获得生产者生产的所有字节。( tByte <> sb->in_avail() )

这是一种内部缓冲问题吗?如果是,如何强制 stringbuf 刷新其内部缓冲区?

最佳答案

A streambuf与 flush 完全不同:写入直接写入缓冲区。有一个 pubsync()如果您要使用派生的对象(例如 filebuf),该成员可能会有所帮助。但这不适用于您的情况。

您的问题肯定来自 sputn() 上的数据竞争is_avail()。通过互斥锁或通过 atomic 保护对流缓冲的访问.如果 m_bIsFinished 不是原子的,并且取决于您对 isFinished() 的实现,可能无法保证线程之间的同步(例如:生产者可以写入到内存,但消费者仍然从 CPU 内存缓存中获取过时的值),这可能导致这种数据竞争。

编辑:

如果您在单个线程中遇到问题,从而消除了任何潜在的竞争条件,它可能来自 streambuf 的实现。我可以在单线程应用程序中使用 MSVC13 体验这一点:

  • 跟踪显示读取的字节数是准确的,但 in_avail() 结果在整个循环中始终小于或等于 tByte。
  • 当读取 streambuf 时,读取了正确的字节总数(因此多于 in_avail() 指示的字节数)。

此行为是合规的。根据 C++ 标准:in_avail() 应返回 egptr() - gptr() 如果读取位置可用,否则返回 showmanyc()。 后者定义为返回序列中可用字符数的估计值唯一的保证是您至少可以阅读in_avail() 没有遇到eof的字节。

解决方法使用 sb->pubseekoff(0,ios::end)- sb->pubseekoff(0,ios::beg); 计算可用字节数,并确保您在您读取您的 streambuf 之前重新定位在 sb->pubseekoff(0,ios::beg)。

关于C++ 如何刷新 std :stringbuf?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/25833193/

31 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com