簡単な説明
PowerShell で文字列データの入力と出力に文字エンコードを使用する方法について説明します。
長い説明
Unicode は、世界中の文字エンコード標準です。 システムは、文字と文字列の操作にのみ Unicode を使用します。 Unicode のすべての側面の詳細については、「Unicode 標準」を参照してください。
Windows では、Unicode 文字セットと従来の文字セットがサポートされています。 Windows コード ページなどの従来の文字セットでは、8 ビット値または 8 ビット値の組み合わせを使用して、特定の言語または地域の設定で使用される文字を表します。
PowerShell では、既定で Unicode 文字セットが使用されます。 ただし、いくつかのコマンドレットには、別の文字セットのエンコードを指定できる Encoding パラメーターがあります。 このパラメーターを使用すると、他のシステムやアプリケーションとの相互運用性に必要な特定の文字エンコードを選択できます。
次のコマンドレットには、Encoding パラメーターがあります。
- Microsoft.PowerShell.Management
- Add-Content
- Get-Content
- Set-Content
- Microsoft.PowerShell.Utility
- Export-Clixml
- Export-Csv
- Export-PSSession
- Format-Hex
- Import-Csv
- Out-File
- Select-String
- Send-MailMessage
バイトオーダーマーク
バイトオーダー マーク (BOM) は、データに使用される Unicode エンコードを示すファイルまたはテキスト ストリームの最初の数バイトに される、
Windows PowerShell では、UTF7を除く Unicode エンコードでは、常に BOM が作成されます。 PowerShell (v6 以降) のデフォルトでは、すべてのテキスト出力の標準色は utf8NoBOM です。
全体的な互換性を最大限に高める場合は、UTF-8 ファイルで BOM を使用しないでください。 Windows プラットフォームでも使用される Unix プラットフォームと Unix-heritage ユーティリティは、BOM をサポートしていません。
同様に、UTF7 エンコードは避ける必要があります。 UTF-7 は標準の Unicode エンコードではなく、すべてのバージョンの PowerShell で BOM なしで記述されます。
Unix に似たプラットフォームで PowerShell スクリプトを作成したり、Visual Studio Code などの Windows のクロスプラットフォーム エディターを使用したりすると、UTF8NoBOMを使用してファイルがエンコードされます。 これらのファイルは PowerShell では正常に動作しますが、ファイルに Ascii 以外の文字が含まれている場合は、Windows PowerShell で破損する可能性があります。
スクリプトで Ascii 以外の文字を使用する必要がある場合は、BOM で UTF-8 として保存します。 BOM がないと、Windows PowerShell では、スクリプトが従来の "ANSI" コードページでエンコードされていると誤って解釈されます。 逆に、UTF-8 BOM を持つファイルは Unix に似たプラットフォームで問題になる可能性があります。
cat、sed、awkなどの多くの Unix ツールや、gedit などの一部のエディターでは BOM の処理方法がわかりません。
Windows PowerShell での文字エンコード
PowerShell 5.1 では、Encoding パラメーターは次の値をサポートしています。
-
AsciiAscii (7 ビット) 文字セットを使用します。 -
BigEndianUnicodeビッグ エンディアンバイト順で UTF-16 を使用します。 -
BigEndianUTF32ビッグ エンディアンバイト順で UTF-32 を使用します。 -
Byte一連の文字をバイト シーケンスにエンコードします。 -
Defaultシステムのアクティブなコード ページ (通常は ANSI) に対応するエンコードを使用します。 -
Oemシステムの現在の OEM コード ページに対応するエンコードを使用します。 -
StringUnicodeと同じです。 -
Unicodeリトル エンディアン バイト順で UTF-16 を使用します。 -
UnknownUnicodeと同じです。 -
UTF32は、リトル エンディアンバイト順で UTF-32 を使用します。 -
UTF7UTF-7 を使用します。 -
UTF8UTF-8 (BOM あり) を使用します。
一般に、Windows PowerShell では既定で Unicode UTF-16LE エンコードが使用されます。 ただし、Windows PowerShell のコマンドレットで使用される既定のエンコードは一貫性がありません。
手記
UTF7を除く Unicode エンコードを使用すると、常に BOM が作成されます。
ファイルに出力を書き込むコマンドレットの場合:
Out-Fileおよびリダイレクト演算子>と>>は UTF-16LE を作成し、これは特にSet-ContentおよびAdd-Contentとは異なります。New-ModuleManifestとExport-Clixmlも UTF-16LE ファイルを作成します。ターゲットファイルが空であるか存在しない場合は、
Set-ContentとAdd-ContentがDefaultエンコーディングを使用します。Defaultは、アクティブなシステム ロケールの ANSI レガシ コード ページで指定されたエンコードです。Export-CsvはAsciiファイルを作成しますが、Append パラメーターを使用する場合は異なるエンコードを使用します (下記を参照)。Export-PSSessionは、既定で BOM を使用して UTF-8 ファイルを作成します。New-Item -Type File -Valueは、BOM レス UTF-8 ファイルを作成します。Send-MailMessageでは、既定でAsciiエンコードが使用されます。Start-Transcriptは、BOM を使用してUtf8ファイルを作成します。 Append パラメーターを使用すると、エンコードが異なる場合があります (以下を参照)。
既存のファイルに追加するコマンドの場合:
Out-File -Appendおよび>>リダイレクト演算子は、既存のターゲット ファイルのコンテンツのエンコードに一致させる試みを行いません。 代わりに、Encoding パラメーターを使用しない限り、既定のエンコードが使用されます。 コンテンツを追加するときは、ファイルの元のエンコードを使用する必要があります。明示的な Encoding パラメーターがない場合、
Add-Contentは既存のエンコードを検出し、新しいコンテンツに自動的に適用します。 既存のコンテンツに BOM がない場合は、DefaultANSI エンコードが使用されます。Add-Contentの動作は PowerShell (v6 以降) でも同じですが、既定のエンコードはUtf8。ターゲット ファイルに BOM が含まれている場合、
Export-Csv -Appendは既存のエンコードと一致します。 BOM がない場合は、Utf8エンコードが使用されます。Start-Transcript -Appendは、BOM を含むファイルの既存のエンコードと一致します。 BOM がない場合、既定ではエンコードがAsciiされます。 トランスクリプト内のデータにマルチバイト文字が含まれている場合、このエンコードによりデータが失われたり、文字が破損したりする可能性があります。
BOM がない場合に文字列データを読み取るコマンドレットの場合:
Get-ContentとImport-PowerShellDataFileでは、DefaultANSI エンコードが使用されます。 ANSI は、PowerShell エンジンがファイルからソース コードを読み取るときにも使用します。Import-Csv、Import-Clixml、およびSelect-Stringは、BOM がない場合にUtf8を想定しています。
PowerShell での文字エンコード
PowerShell (v7.1 以降) では、Encoding パラメーターは次の値をサポートしています。
-
ascii: ASCII (7 ビット) 文字セットのエンコードを使用します。 -
ansi: 現在のカルチャの ANSI コード ページのエンコーディングを使用します。 このオプションは PowerShell 7.4 で追加されました。 -
bigendianunicode: ビッグ エンディアンバイト順を使用して UTF-16 形式でエンコードします。 -
bigendianutf32: ビッグ エンディアンバイト順を使用して UTF-32 形式でエンコードします。 -
oem: MS-DOS およびコンソール プログラムの既定のエンコードを使用します。 -
unicode: リトル エンディアンバイト順を使用して UTF-16 形式でエンコードします。 -
utf7: UTF-7 形式でエンコードします。 -
utf8: UTF-8 形式 (BOM なし) でエンコードします。 -
utf8BOM: バイト オーダー マーク (BOM) を使用して UTF-8 形式でエンコードします。 -
utf8NoBOM: バイト オーダー マーク (BOM) なしで UTF-8 形式でエンコードします -
utf32: リトル エンディアンバイト順を使用して UTF-32 形式でエンコードします。
PowerShell の既定では、すべての出力が utf8NoBOM に設定されています。
PowerShell 6.2 以降では、Encoding パラメーターを使用すると、登録済みのコード ページ (-Encoding 1251など) の数値 ID や、登録されたコード ページの文字列名 (-Encoding "windows-1251"など) も使用できます。 詳細については、Encoding.CodePageの .NET ドキュメントを参照してください。
PowerShell 7.4 以降では、ANSI パラメーターの 値を使用して、手動で指定しなくても、現在のカルチャの ANSI コード ページの数値 ID を渡すことができます。
既定のエンコードの変更
PowerShell には、既定のエンコード動作を変更するために使用できる 2 つの既定の変数があります。
$PSDefaultParameterValues$OutputEncoding
詳細については、about_Preference_Variablesを参照してください。
PowerShell 5.1 以降では、リダイレクト演算子 (> と >>) は、Out-File コマンドレットを呼び出します。 そのため、次の例に示すように、$PSDefaultParameterValues 基本設定変数を使用して、それらの既定のエンコードを設定できます。
$PSDefaultParameterValues['Out-File:Encoding'] = 'utf8'
Encoding パラメーターを持つすべてのコマンドレットの既定のエンコードを変更するには、次のステートメントを使用します。
$PSDefaultParameterValues['*:Encoding'] = 'utf8'
重要
このコマンドを PowerShell プロファイルに配置すると、ユーザー設定は、エンコードを明示的に指定しないすべてのコマンドとスクリプトに影響を与えるセッショングローバル設定になります。
同様に、同じように動作させるこのようなコマンドをスクリプトまたはモジュールに含める必要があります。 これらのコマンドを使用すると、別のユーザー、別のコンピューター、または別のバージョンの PowerShell で実行した場合でも、コマンドレットの動作が同じになります。
自動変数 $OutputEncoding は、PowerShell が外部プログラムと通信するために使用するエンコードに影響します。 出力リダイレクト演算子と PowerShell コマンドレットがファイルへの保存に使用するエンコードには影響しません。
こちらも参照ください
PowerShell