You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何用Inno Setup保存带BOM的UTF-16(UCS-2)编码文本文件?

刚好之前做过类似的需求,我来给你梳理下Inno Setup中保存带BOM的UTF-16(UCS-2)文件的正确实现方式:

如何在Inno Setup中保存带BOM的UTF-16(UCS-2)编码文件

首先明确:Windows平台最常用的UTF-16编码是UTF-16LE(小端序),对应的BOM标识是#$FF#$FE;如果需要大端序的UTF-16BE,BOM则是#$FE#$FF。以下以最常用的UTF-16LE为例说明。

方法一:高效写入(推荐)

Inno Setup中的String类型本身就是UTF-16LE编码的Unicode字符串,所以我们可以直接将字符串的原始字节写入文件,再加上BOM即可,无需逐个字符拆分处理。

保存单个字符串到UTF-16LE文件(带BOM)

procedure SaveStringToUTF16LEFile(const FileName: String; const Content: String);
var
  Stream: TFileStream;
begin
  // 创建或覆盖目标文件
  Stream := TFileStream.Create(FileName, fmCreate);
  try
    // 写入UTF-16LE的BOM标识(FF FE)
    Stream.WriteBuffer(#$FF#$FE, 2);
    // 直接写入字符串的Unicode字节:每个WideChar占2字节,总长度为Length(Content)*2
    if Length(Content) > 0 then
      Stream.WriteBuffer(Content[1], Length(Content)*2);
  finally
    Stream.Free;
  end;
end;

保存字符串数组到UTF-16LE文件(带BOM,每行一个字符串)

如果需要实现类似SaveStringsToUTF8File的数组保存功能,只需循环写入每行内容,再加上UTF-16LE格式的换行符即可:

procedure SaveStringsToUTF16LEFile(const FileName: String; const Strings: TStrings);
var
  Stream: TFileStream;
  I: Integer;
  Line: String;
begin
  Stream := TFileStream.Create(FileName, fmCreate);
  try
    // 写入BOM标识
    Stream.WriteBuffer(#$FF#$FE, 2);
    // 循环写入每行内容
    for I := 0 to Strings.Count - 1 do
    begin
      Line := Strings[I];
      if Length(Line) > 0 then
        Stream.WriteBuffer(Line[1], Length(Line)*2);
      // 写入UTF-16LE格式的换行符(CRLF,占4字节)
      Stream.WriteBuffer(#13#10, 2*SizeOf(WideChar));
    end;
  finally
    Stream.Free;
  end;
end;

方法二:修正你现有的代码

你的现有代码已经在模拟UTF-16LE的字节写入逻辑,但缺少BOM标识,且逐个字符处理的方式比较冗余。如果要基于你的代码修改,只需在循环前加入BOM的写入即可:

procedure SaveMyStringToUTF16File(const FileName: String; const aString: String);
var
  i: Integer;
  Stream: TFileStream;
begin
  Stream := TFileStream.Create(FileName, fmCreate);
  try
    // 先写入UTF-16LE的BOM标识
    Stream.Write(#$FF, 1);
    Stream.Write(#$FE, 1);
    // 你的原有写入逻辑
    for i := 1 to Length(aString) do
    begin
      Stream.Write(aString[i], 1);
      Stream.Write(#0, 1);
    end;
  finally
    Stream.Free;
  end;
end;

不过还是更推荐方法一的写法,直接写入整个字符串的字节更高效简洁。

注意事项

  • 如果需要保存UTF-16BE编码,只需将BOM改为#$FE#$FF,并且将每个WideChar的字节顺序反转后写入(先写高字节,再写低字节)。
  • Inno Setup的TFileStream是二进制流,写入的字节不会被自动转换,能确保编码的准确性。

内容的提问来源于stack exchange,提问作者none

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.11 07:25:49