【问题标题】:How to write binary data into stdout in Delphi?Delphi如何将二进制数据写入标准输出?
【发布时间】:2013-03-21 07:29:39
【问题描述】:

如何从 Delphi 控制台应用程序写入标准输出?

这是我尝试过的。我根据我能找到的信息操纵了这个简单的测试应用程序,从磁盘读取文件并将其输出到控制台标准输出:

program ConsoleOut;
{$APPTYPE CONSOLE}
uses
  Classes, Windows, SysUtils;

var
  S: TMemoryStream;
  OutputStream: THandleStream;
  ss: string;
  Buffer: PByte;
  i: Integer;
begin
  S := TMemoryStream.Create;
  S.LoadFromFile('1.jpg');
  S.Seek(0, soFromBeginning);

  //Am I right that from now on writing to OutputStream will write to stdout?
  OutputStream := THandleStream.Create(GetStdHandle(STD_OUTPUT_HANDLE));

  GetMem(Buffer, S.Size);
    S.ReadBuffer(Buffer^, S.Size);
    i := OutputStream.Write(Buffer^, S.Size); //i = 0 here for some reason
  FreeMem(Buffer, S.Size);

  Writeln(i, ' byte written to output');
  Readln(ss); //Don't exit app to read previous line
  S.Free;
end.

但由于某种原因它失败了。您能否指导我以正确的方式写入标准输出?

【问题讨论】:

  • 很好奇为什么要向控制台写入二进制噪声?你提到了一些关于文本到语音的东西。为什么不命名管道?
  • 命名管道相对于标准输出有什么优势?
  • 在 Windows 上专为严肃的数据传输而不是用户界面而设计。 Unix 标准输出通常用作匿名数据管道。 Dos 和 Windows 不经常使用它。正如你所了解的。

标签: delphi console stdout


【解决方案1】:

你的方法是正确的。但是,如果标准输出连接到控制台,那么您的代码将失败。在流写入之后调用GetLastError 会显示错误代码ERROR_NOT_ENOUGH_MEMORY:

没有足够的存储空间来处理这个命令。

如果您将标准输出重定向到文件,那么您的代码将正常工作。当然,您并不想将二进制数据发送到控制台。这只会将无法读取的内容放在控制台上,并使计算机发出烦人的哔哔声!

如果您必须输出到控制台,那么您需要找出控制台设备缓冲区的大小并以适当大小的块写入它。我必须承认,我不确定你是怎么做到的。你可以使用试错法,但这对我没有吸引力。想必有办法查询控制台查到信息。

查看WriteConsole的文档,似乎64K是上限。事实上,如果我将空格写入您的句柄流,那么我可以一次写入近 64K。但是,如果我写原始的 JPEG 二进制数据,那么它会更早地给出。所以我认为这也是问题的一部分——不要将 JPEG 文件转储到控制台。

另一条评论。由于您将文件的内容读入内存流,因此无需分配中间缓冲区。可以直接写S.Memory^。

【讨论】:

  • 感谢您的提示,我认为如果控制台为空,则无法正常工作,但是将标准输出重定向到文件(“appname.exe > out.jpg”)就可以了。
  • 附注:我正在开发一个需要生成文本到语音并将其输出到标准输出的应用程序,所以是的,这是二进制数据和很多数据(几 Mb​​)。但是你的回答涉及到很多方面,所以请不要剪,对别人有用)
  • @KromStern:你最后的评论毫无意义。如果你正在做text to speech to stdout 然后将stdout 重定向到一个文件,你可以简单地做text to speech to file 并去掉stdout 中间人。写入控制台以立即将该输出重定向到文件是没有意义的。
  • @Ken White:我需要将 tts 写入标准输出,以便其他程序员可以将其安装到他的设置中。我正在测试 stdout > 文件以检查我的部分是否正确。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2010-10-28
  • 2014-11-09
  • 2012-10-13
  • 2010-12-01
  • 2019-09-04
相关资源
最近更新 更多