C# と VB.NET の質問掲示板

ASP.NET、C++/CLI、Java 何でもどうぞ

C# と VB.NET の入門サイト

Re[3]: byte型配列のコピー


(過去ログ 20 を表示中)

[トピック内 10 記事 (1 - 10 表示)]  << 0 >>

■8433 / inTopicNo.1)  byte型配列のコピー
  
□投稿者/ tk (6回)-(2007/09/29(Sat) 15:57:01)

分類:[C#] 

いつもお世話になっております。恐縮ですが質問させてください。

やりたい事はテキストファイルを読み込んで改行コード(0x0d, 0x0a, もしくは0x0d0a)ごとに
バイト型配列にいれてListにAdd()してくことなんですが、

方法としては
1.FileStream.Read()で一度ファイルを全部読み込む
2.頭からそのバイト配列を見てって、0x0dが見つかったら、見つかるまでの分byteを確保して(0x0aが次にあったらもう1バイト)
3.コピーしてListにAdd()

というような感じです。ここで効率悪いなぁと感じているのはそもそも既にファイル全部のバイト分確保しているわけなので、
1行ごとにまた確保するとファイルの2倍確保することになることです。

もっと良い方法ありますでしょうか。1行ごとのByte型配列は1行分だけポインタのように指すみたいな
事ができたらいいなぁと思っています。

引用返信 編集キー/
■8434 / inTopicNo.2)  Re[1]: byte型配列のコピー
□投稿者/ tk (7回)-(2007/09/29(Sat) 15:59:20)
すいません、あとバイト配列のコピーの方法がよくわからないです。

上述のファイルのバイト配列から1部分だけバイト配列コピーをするのに
Byte.CopyTo()メソッドを使うにはどこからコピーするかは指定できるけど
どこまでは指定できないので、例外が発生しました。
引用返信 編集キー/
■8436 / inTopicNo.3)  Re[1]: byte型配列のコピー
□投稿者/ 渋木宏明(ひどり) (428回)-(2007/09/29(Sat) 18:10:22)
渋木宏明(ひどり) さんの Web サイト
> やりたい事はテキストファイルを読み込んで改行コード(0x0d, 0x0a, もしくは0x0d0a)ごとに
> バイト型配列にいれてListにAdd()してくことなんですが、

本当に byte 型の配列である必要があるんですか?
ファイルから読み込んだ各行を文字列として扱うなら、StreamReader.ReadLine() で1行づつ文字列として読み込むことが出来ます。

> というような感じです。ここで効率悪いなぁと感じているのはそもそも既にファイル全部のバイト分確保しているわけなので、
> 1行ごとにまた確保するとファイルの2倍確保することになることです。

でも、全行を読み込んだら「ファイル全体を読み込んだ byte 配列」は用無しでしょ?
であれば、そんなに神経質になる必要はないような。

どうしても気になるなら、1度メモリに全部読むのをやめて、Stream.Read() で1バイトづつ読み込んで。。。とすればいいんじゃないでしょうか。

引用返信 編集キー/
■8437 / inTopicNo.4)  Re[2]: byte型配列のコピー
□投稿者/ 渋木宏明(ひどり) (429回)-(2007/09/29(Sat) 18:12:23)
渋木宏明(ひどり) さんの Web サイト
> 上述のファイルのバイト配列から1部分だけバイト配列コピーをするのに
> Byte.CopyTo()メソッドを使うにはどこからコピーするかは指定できるけど
> どこまでは指定できないので、例外が発生しました。

Array.Copy() なら、開始位置と長さも指定できるはずです。
引用返信 編集キー/
■8438 / inTopicNo.5)  Re[2]: byte型配列のコピー
□投稿者/ tk (8回)-(2007/09/29(Sat) 18:20:51)
渋木様、ご回答有難うございます。

> 本当に byte 型の配列である必要があるんですか?
> ファイルから読み込んだ各行を文字列として扱うなら、StreamReader.ReadLine() で1行づつ文字列として読み込むことが出来ます。
すいません。経緯を書き忘れてました。改行コードも欲しくて、StreamReader.ReadLine()だと文字列だけみたいなので
バイト単位で読み込むわけです。

> でも、全行を読み込んだら「ファイル全体を読み込んだ byte 配列」は用無しでしょ?
> であれば、そんなに神経質になる必要はないような。
確かに!そのスコープ抜けたらGCで消えますね。コードとして美しくないかなぁって
思って気になってしまいました。

ありがとうございます。

一応バイトのコピーは改行コードがわかったらfor文で
dest[i] = src[j]
というような感じで普通にコピーしようと思います。
引用返信 編集キー/
■8439 / inTopicNo.6)  Re[3]: byte型配列のコピー
□投稿者/ tk (9回)-(2007/09/29(Sat) 18:24:32)
行き違いで書き込んですみません。

> Array.Copy() なら、開始位置と長さも指定できるはずです。
初耳でした!使ってみます!

解決済み
引用返信 編集キー/
■8441 / inTopicNo.7)  Re[3]: byte型配列のコピー
□投稿者/ 渋木宏明(ひどり) (430回)-(2007/09/29(Sat) 19:56:51)
渋木宏明(ひどり) さんの Web サイト
> 一応バイトのコピーは改行コードがわかったらfor文で
> dest[i] = src[j]
> というような感じで普通にコピーしようと思います。

あー、そういう使い方なわけですか。

なら、特別高速でなくてもいいなら、MemoryStream に追記していくようにして、「行」が確定したら MemoryStream.ToArray() で byte 型配列化する方が、コードが簡単になる予感。

引用返信 編集キー/
■8442 / inTopicNo.8)  Re[3]: byte型配列のコピー
□投稿者/ 渋木宏明(ひどり) (431回)-(2007/09/29(Sat) 20:01:03)
渋木宏明(ひどり) さんの Web サイト
> コードとして美しくないかなぁって
> 思って気になってしまいました。

ものすごい巨大なファイルを扱わなければならないなら別ですが、その場合は「全行を byte 型配列のリストで持つ」ところから考え直さなくちゃらないです。

引用返信 編集キー/
■8449 / inTopicNo.9)  Re[4]: byte型配列のコピー
□投稿者/ tk (10回)-(2007/09/30(Sun) 17:47:08)
渋木様

いつもわかりやすい回答と革新的な提案ありがとうございます。
感謝しています。

> なら、特別高速でなくてもいいなら、MemoryStream に追記していくようにして、「行」が確定したら MemoryStream.ToArray() で byte 型配列化する方が、コードが簡単になる予感。
MemoryStreamのmsdn読んできました。なるほどこんな管理の仕方があるんですね。勉強になりました。
ただ、できれば高速がいいので、最初の渋木様の案のArray.ToCopy()を使わせて頂きます!

おかげさまで、for文でくるくる1Byteごと代入していたのが、
byte[] destAry = new byte[toRtn];
Array.Copy(srcAry, srcAry, destAry, 0, toRtn);
の2行でできるようになりましたし、美しいし(たぶん)早いと思いました!(主観によりますが・・・)

>「全行を byte 型配列のリストで持つ」ところから考え直さなくちゃらないです。
最終的にやりたいことが、2つのテキストファイルを行ごとで比較したいのですが
片方にあって片方にないところは空の行を入れたいんです。
そこで、行ごとで比較するにも、空行をinsertするにもList<>って使いやすいなぁと思った次第です。

他にもしまた提案があれば、是非聞きたいです。この度は本当にありがとうございました。

解決済み
引用返信 編集キー/
■8450 / inTopicNo.10)  Re[5]: byte型配列のコピー
□投稿者/ tk (11回)-(2007/09/30(Sun) 17:48:56)
> Array.Copy(srcAry, srcAry, destAry, 0, toRtn);
Array.Copy(srcAry, srcIndex, destAry, 0, toRtn);
でした。失礼しました。
引用返信 編集キー/


トピック内ページ移動 / << 0 >>

このトピックに書きこむ

過去ログには書き込み不可

管理者用

- Child Tree -