命令行查找替换后特殊字符变成问号

Special characters become question marks after Command line find and replace

我有一个文本文件input.xlf

  <trans-unit id="loco:5e7257a0c38e0f5b456bae94">
    &lt;source&gt;Login</source>
    <target>登入</target>
    <note>Login Header</note>
  </trans-unit>

基本上我需要将 &lt; 替换为 < 并将 &gt; 替换为 '>',所以我 运行 下面的脚本

runner.bat

powershell -Command "(gc input.xlf) -replace '&lt;', '<' | Out-File -encoding ASCII output.xlf";
powershell -Command "(gc output.xlf) -replace '&gt;', '>' | Out-File -encoding ASCII  output.xlf";

以上一直有效,直到我注意到下面的输出

  <trans-unit id="loco:5e7257a0c38e0f5b456bae94">
    <source>Login</source>
    <target>??????</target>
    <note>Login Header</note>
  </trans-unit>

我尝试删除编码,但现在我得到了

 <trans-unit id="loco:5e7257a0c38e0f5b456bae94">
   <source>Login</source>
   <target>登入</target>
   <note>Login Header</note>  
 </trans-unit>

下面是我想要的输出

  <trans-unit id="loco:5e7257a0c38e0f5b456bae94">
    <source>Login</source>
    <target>登入</target>
    <note>Login Header</note>
  </trans-unit>

(潜在)两个字符编码问题:

  • 输出上,使用-Encoding Ascii保证“有损”音译任何非ASCII -range characters to literal ? 个字符。

    • 要保留所有字符,您必须选择Unicode编码,例如-Encoding Utf8
  • 输入时,您必须确保PowerShell正确读取输入文件。

    • 具体来说,Windows PowerShellBOM-less UTF-8 文件误解为 ANSI-编码,所以你也需要使用 -Encoding Utf8Get-Content

此外,您可以通过 单个 powershell.exe 调用,并且还可以 优化 此调用:

powershell -Command "(gc -Raw -Encoding utf8 input.xlf) -replace '&lt;', '<' -replace '&gt;', '>' | Set-Content -NoNewLine -Encoding Utf8 output.xlf"
  • 使用 -Rawgc (Get-Content) 读取文件 作为一个整体 而不是 [= =44=]行数组,这加快了-replace操作。

  • 你可以-replace操作

  • 对于已经是文本(字符串)的输入,Set-Content 通常是更快的选择。[1]
    -NoNewLine 防止附加尾随换行符。


[1] 在这里几乎没有区别,只要 一个 单个 字符串被写入,但是有许多输入字符串(逐行输出)它可能 - 参见 .