0

以下のハッキングされたコードから得られる結果がわかりません。誰か説明してください。UNICODEでエンコードされたテキスト ファイルを読み取るときにのみ発生します。

fs = File.Open(fileName, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);

// read from start
byte[] lne = new byte[100];
int actual = fs.Read(lne, 0, lne.Length);
string line = Encoding.Unicode.GetString(lne, 0, actual); // ok readable stuff as expected
string line1 = Encoding.BigEndianUnicode.GetString(lne, 0, actual); // fail as expected

// move down into the file
fs.Seek(-150, SeekOrigin.End);
fs.ReadByte(); // take this out, works ok!

lne = new byte[100];
actual = fs.Read(lne, 0, lne.Length);
line = encoding.GetString(lne, 0, actual); // fail non readable stuff - NOT EXPECTED
line1 = Encoding.BigEndianUnicode.GetString(lne, 0, actual); // SUCCESS, readable - huh!

明らかに、コードは「現実世界」ではなく、実際のコードが行っていることの内訳にすぎません。

最初の Encoding.Unicode.GetString の後、変数 'line' に読みやすいデータが表示され、予想どおり 'line1' に不適切なデータが表示されます。

2 番目の Encoding.Unicode.GetString の後、完全ながらくたが表示されます (日本語/中国語はわかりません) が、line1 にはファイルから取得した読み取り可能なデータが含まれるようになりました。

ReadByte を取り出すと、すべてが期待どおりに機能します。

なぜこれが起こっているのか、誰にでもアイデアがあります。

ティア。

4

2 に答える 2

2

ストリームの末尾から 100 バイトを引いた位置に移動しています。次に、1 バイト (ストリームの末尾から 99 バイトを引いたもの) を読み取り、その後 100 バイトを読み取ろうとしています。これにより、ストリームの外に 1 バイトかかります。

于 2013-09-27T15:27:11.793 に答える
0

Unicode 文字列は 2 バイトで、ASCII 文字列の場合は次のようになります。

0x41, 0, 0x42, 0, 0x43, 0 ...  // {ASCII code for A}, 0,...

したがって、逆の順序 ( BigEndianUnicode) でバイトを読み取ると、意味のない文字が得られます。上記の文字列は0x4100, 0x4200, 0x4300 ...代わりに0x0041,...

奇数オフセット (ファイル コードの終わりからシークする) で読み取りを開始すると、同様のことが起こります。ASCII テキストを含むバイトは次のようになります。

0, 0x41, 0, 0x42, 0, 0x43 ...

これは次のように読まれます0x4100, 0x4200, 0x4300...

ReadByte最初の 0 を取り出すので、文字の途中ではなく文字の先頭から読み取り、シーケンスは有効な ASCII のみの Unicode 文字列になります (最後の文字が無効になる可能性があります:

0x41, 0, 0x42, 0, 0x43,...
于 2013-09-27T16:14:28.327 に答える