都合のいい質問だと分かってて質問しています。
今、データの読み込みプログラムを作っています。
件数は12万件(11MB)です。
・データはCSV形式になっており、区切りはカンマです。
・"" で囲まれたカラムとそうでないカラムがあり、"" で囲まれたカラムの一部には、データとしてカンマが含まれていることがあります。
・また、データにはエスケープシーケンスを含むことが許されており、 \" という文字は囲み記号であると認識してはいけません。
このようなルールのとき、
@data = split( /,/, $line );
というロジックでは分割できませんよね。
なんで、物凄い複雑なロジックで分割を行う xsplit という独自の関数を作って分割しています。
ところが、1行ごとにこの xsplit を使用しなければならないため、データが12万件もあると、読み込みだけで15~18秒もかかってしまいます。( split だと3秒で終わります)
で、少しでもこの時間を縮めるために、上記のルールを崩さずに split の /,/ の部分を変更するだけで分割を行うことはできないもんでしょうか。
何か思いついた方がいらっしゃいましたら、よろしくお願いします。
(ちなみに拡張モジュール類などの、環境によって動いたり動かなかったりするような物は使えないということでお願いします)
No.3ベストアンサー
- 回答日時:
No.1 で紹介されたページのアルゴリズムは、エスケープシーケンスに対応していません。
これを対応させると以下のようになります。(ちょっと簡素化してます。)
chomp $line; # 改行が既に削除されていれば不要です。
@data = "$line," =~ /("[^"]*(?:\\"[^"]*)*"|[^,]*),/g;
$line の値が
ABC,"foo,bar","hoge=\"baz,123\"",\"ok?,:-)\"
だとすると、@data の要素は
ABC
"foo,bar"
"hoge=\"baz,123\""
\"ok?
:-)\"
となります。
また、要素に含まれる囲みクォートを削除し、\" を " に戻すには、
@data = map { s/^"(.*)"$/$1/; s/\\"/"/g; $_ }
"$line," =~ /("[^"]*(?:\\"[^"]*)*"|[^,]*),/g;
とします。すると @data の要素は
ABC
foo,bar
hoge="baz,123"
"ok?
:-)"
となります。
こちらの方法は、No.2 で紹介された Text::ParseWords を使った方法と同じ結果になりますので、ベンチマークを取って早かった方を使われるとよいでしょう。
No.2
- 回答日時:
Text::ParseWordsモジュールでできます。
例)
use Text::ParseWords;
@b=quotewords(",",0,"AAA,\"b\",cc");
p join("-",@b);
AAA-b-cc
以上です
No.1
- 回答日時:
要するに、
・データはCSV形式になっており、区切りはカンマです。
・"" で囲まれたカラムとそうでないカラムがあり、"" で囲まれたカラムの一部には、データとしてカンマが含まれていることがあります。
・また、データにはエスケープシーケンスを含むことが許されており、 \" という文字は囲み記号であると認識してはいけません。
を処理できる、正規表現があれば良いのですよね。ピッタリのものがあります。
http://www.din.or.jp/~ohzaki/perl.htm#CSV2Values
これを関数化すれば良いと思います。
参考URL:http://www.din.or.jp/~ohzaki/perl.htm#CSV2Values
お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!
関連するカテゴリからQ&Aを探す
おすすめ情報
- ・漫画をレンタルでお得に読める!
- ・一回も披露したことのない豆知識
- ・これ何て呼びますか
- ・チョコミントアイス
- ・初めて自分の家と他人の家が違う、と意識した時
- ・「これはヤバかったな」という遅刻エピソード
- ・これ何て呼びますか Part2
- ・許せない心理テスト
- ・この人頭いいなと思ったエピソード
- ・牛、豚、鶏、どれか一つ食べられなくなるとしたら?
- ・あなたの習慣について教えてください!!
- ・ハマっている「お菓子」を教えて!
- ・高校三年生の合唱祭で何を歌いましたか?
- ・【大喜利】【投稿~11/1】 存在しそうで存在しないモノマネ芸人の名前を教えてください
- ・好きなおでんの具材ドラフト会議しましょう
- ・餃子を食べるとき、何をつけますか?
- ・あなたの「必」の書き順を教えてください
- ・ギリギリ行けるお一人様のライン
- ・10代と話して驚いたこと
- ・家の中でのこだわりスペースはどこですか?
- ・つい集めてしまうものはなんですか?
- ・自分のセンスや笑いの好みに影響を受けた作品を教えて
- ・【お題】引っかけ問題(締め切り10月27日(日)23時)
- ・大人になっても苦手な食べ物、ありますか?
- ・14歳の自分に衝撃の事実を告げてください
- ・架空の映画のネタバレレビュー
- ・「お昼の放送」の思い出
- ・昨日見た夢を教えて下さい
- ・ちょっと先の未来クイズ第4問
- ・【大喜利】【投稿~10/21(月)】買ったばかりの自転車を分解してひと言
- ・メモのコツを教えてください!
- ・CDの保有枚数を教えてください
- ・ホテルを選ぶとき、これだけは譲れない条件TOP3は?
- ・家・車以外で、人生で一番奮発した買い物
- ・人生最悪の忘れ物
- ・【コナン30周年】嘘でしょ!?と思った○○周年を教えて【ハルヒ20周年】
- ・10秒目をつむったら…
- ・人生のプチ美学を教えてください!!
- ・あなたの習慣について教えてください!!
- ・都道府県穴埋めゲーム
デイリーランキングこのカテゴリの人気デイリーQ&Aランキング
-
マクロを使ってフォルダー内に...
-
CSVファイルの中で、「 , 」カ...
-
EXCELからCSVにすると余計なカ...
-
VB2005のTextBoxでカン...
-
VC++のエディトボックスについて
-
エクセルで数値を全角文字(カ...
-
Delphi 文字列の中のタブをコン...
-
データにカンマが入ったCSVデー...
-
C#で、テキストボックスの入力...
-
WORDで改ページすると時々グレ...
-
カンマ区切りの数字をCSVフ...
-
PowerShellの繰り返し処理の最...
-
openoffice calcで#DIV/0! の...
-
CSVの定義
-
英数字のみ全角から半角に変換
-
Accessで日付や数値を全角で表...
-
いまスマホからカードの申込み...
-
住宅にカナを入力する際に丁目...
-
jcode.pl
-
全角英数字の必要性が理解できない
マンスリーランキングこのカテゴリの人気マンスリーQ&Aランキング
-
CSVファイルの中で、「 , 」カ...
-
エクセルで数値を全角文字(カ...
-
EXCELからCSVにすると余計なカ...
-
カンマ区切りの数字をCSVフ...
-
マクロを使ってフォルダー内に...
-
CSVの定義
-
WORDで改ページすると時々グレ...
-
Excelについて質問です。 セル...
-
カンマ区切り
-
データにカンマが入ったCSVデー...
-
C#で、テキストボックスの入力...
-
何故、日本は未だに数字を3桁...
-
[VBA][Excel]クリップボードか...
-
VBAでtxtファイルを読み込む際...
-
パス区切りの文字について
-
ひとつの命令を複数行に記述
-
PHP カンマをエスケープしたい...
-
3桁ごと?4桁ごと?コンマの...
-
CSVファイル中の不規則な数のス...
-
エクセル セルの書式設定 ユ...
おすすめ情報