さ み だ れ 雑 記 | 17 | 1999年8月16日 |
CSV騒動の巻
第1章:発端
話は、ダイセル化学の「日本の流行歌史大系」にさかのぼる。このホームページ内に掲載しているデータベースのことである。
もともとはレコード会社別のCDを年代順に再編集してCD-Rに書き込むための基礎データとしてWindowsの桐で作っていた。桐とはデータベース・ソフトである。
いやいやもっとくわしくいうと、Access95で作っていた。これもデータベースソフトである。が、Accessではデータを記入しているとある文字数を越えると受け付けなくなるという現象が起こったのであった。
項目数を増やすのは嫌いだ!
ということでDosの時代に慣れ親しんだ桐のWindows版を購入してしまったのであった。
(と思うんだが記憶が定かではない。政治家の「記憶にない」というのも2割程度は本当であろうと思う私はお人好し?)
さて、手元にデータがあるのである。公開したい。
と、思っていたら「ネットサーフレスキュー」というサイトでPerl版簡易データベースを見つけた。これはもうウンロードである。
プログラムを読むと使えそうではないか!
そのプログラムはデータをCSV形式で保存していた。
CSVとはデータをコンマ(カンマともいうがわしはコンマの方が好きじゃ)で区切る形式である。
英語でいうと、comma sparated value:「コンマで区切られた値」である。
まんまなネーミングである。
a,b,c,d,e
である。
桐で「テキストで書き出し」を選ぶと、CSV形式で書き出してくれる。
詳しく言うと、「テキスト形式で書き出す」とき、区切り文字を指定することが出来るのであるが、デフォルトがコンマなので、デフォルトではCSV形式になるのであった。
さて、これで目途はたった。ということでPerl始めて2ヶ月にならない初心者が分からないなりにつついて、動くんだからPerlはすごい。
やったあ!
であった。
ところがである。
あれま、である。
うまくいかないデータがある。
コンマでデータを区切ると言っても、元のデータにコンマが含まれていたら?
つまり
a,b
というデータがあると?
"a,b"
とダブルクオーテーションマークでデータをくくって書き出すのであった。
簡易データベースのプログラムは、
split(/\,/,$data)
という処理、つまりコンマを区切り文字として切り出せというものであった。
よって
"a,b"
を
"a
b"
の2つに切り出したのであった。
これが、CSV騒動の発端であった。
第2章:Excelの怪
発端の解決は簡単であった。
a,b
を
a、b
と書き換えて終わりである。発端なんだから微笑ましいもんである。これで正しく表示されるようになった。
次
である。
ネット上で電話代使ってデータベースを使うというのはやめたいもんである。出来たらデータをダウンロードしたいと誰しも思うであろう。もちろん気になるデータだったらの話であるが。
ということでダウンロード出来るようにしようである。でもってHTMLファイルに次の1行を入れたのである。
<a href="aisel.csv">データベース・ファイルをダウンロードする。(daisel.csv 84KB)</a>
とろこがぎっちょんちょん。(「ところがぎっちょんちょん」が標準的な日本語である)
ネスケで試すと、画面表示するんである。あんれま。IEでやってみるべえか。
あれ?あれ?
れれれ
ぬあんと、IEの画面内にExcel 97が立ち上がる!
し、し、しかも、なんじゃこれ??
04/03 と表示すべきが、4月3日
絶句。
もとの04/03と表示するように設定しようとしてもよう分からん。もう腹が立つ。どうぜ表計算ソフトなんてそんなに使わないんじゃ。消したる!
Excel はめでたくアンインストールされてしまいました、とさ。めでたしめでたし。。。(で終わらなかったのだが、、、、、)
第3章:コンマ入りCSV
さて、次のテーマは、コンマがデータに入っているCSVである。
今は昔、Windows3.1の時代。Dosのソフトはまだまだ力を保持していたのであった。その時代には、表計算は1-2-3、ワープロは一太郎(松ってのもあった)、そして、データベースといえば、桐であった。
その桐5でちまちまと入力していた、もう一つのデータベースが存在した。それが音楽年表としてアップしてしまったものの原型である。(原型には音楽以外の項目も若干含まれていた)
これはコンマをふんだんに使ったデータベースである。
何とかこれを処理できないものか。。。。。。
アップするデータの内容よりも、Perlでいかに処理するかということに熱中している私であった。
こんどは「とほほのWWW入門」というサイトである。ここに「ラウンジ」というBBSがあり、多くの質疑応答が寄せられている。検索が出来る。
csvと入力して検索。
するとぞろぞろ出てくる。それらしい奴を表示させると、、、、、、
あるではないか!!!!!!!
つまり、ある区切り文字で連結された要素の中に、区切り文字が入っていた場合にはどの様にしたらよいのか
といったことですが、ご教授方よろしくお願いします。 因みに、csv ファイルの場合は @y = (); push (@y, $+) while $x =~ m{ "([^\"\\]*(?:\\.[^\"\\]*)*)",? | ([^,]+),?| , }gx; push (@y, undef) if substr ( $x, -1, 1) eq ',' ; でうまくいったのですが、これのカンマの所を<>に置き換えると、最後の要素が出てこないのですが、 |
それにしてもシンプルな split(/\,/,$data) とはえらいちがいであるが、使っちゃえ。
動いた。
アップじゃ。アップじゃ。
お調子者の私であった。
Perlにはまった私の頭に、ほほほ、とアイデアがひらめいた。
Excelでファイルを、HTMLで書き出す機能がある。以前試したことがあるが、ファイルはでかくなるは、フォントの字体を勝手に指定しくさるは、使い勝手が悪い。csvを自動でHTMLのテーブルに変換するPerlプログラムは出来ないものか?
やってみよう。
基本はデータベースのプログラムと同じである。
違うのは、データベースの場合は、項目数に応じてプログラムを書いている。項目数固定である。項目数を可変に出来るか? 基本的にはそんだけである。
やってみよう。
できた。
ほんと?
ダイセルの日本流行歌史。
OK である。
音楽年表。
あんが〜
項目数が多い!
何故じゃ、何故なんじゃ〜?
調べる。
調べる。
調べる。
問題は、データの中のコンマ、だけではなかった。
データの中でコンマを使った処理のため、ダブルクオーテーションマークを使うのは上で述べた。
a,b
というデータがあると
"a,b"
とダブルクオーテーションマークでデータをくくって書き出すのであった。
では、元のデータが
"a,b"
の場合は
"""a,b"""
と書き出すのである。このような箇所が、誤って、ではないが、希望する形に切り出せないのであった。
K's K[E-Mail] 1999/08/10(火) 01:34:32
kofukuさんのデータ内にカンマが含まれる場合のcsvの処理を見させて貰って、使わせていただきました。 すると、うまく切り取ることが出来ない行があって、その行には、元のデータにダブルクオーテーションマークが含まれていて("tohoho")、それが、("""tohoho""")のようにcsvに変換されていました。 やってみたのですが、Perlを始めて2ヶ月程度では歯が立ちません。 どうかご教授願います。なお、元のデータにコンマとダブルクオーテーションマークがともに含まれている場合もあるので、 a,"a,b","""a""","""a, b, and c""" を、正しく a と a,b と"a"と"a, b, and c"に区切る方法ということになると思います。よろしくお願いいたします。 |
泣きついた私であった。
すると、次の日にもうレスが。。。。
B-Cus 1999/08/10(火) 05:08:36
うまくいくかどうか自信はないけど $_='a,"a,b","""a""","""a, b, and c"""'; while ($_){ s/^("*)(".*?")\1(,|$)// || s/^()(.*?)(,|$)//; print "$2\n"; } とか。 K's K 1999/08/11(水) 01:40:02 B-Cusさんのをやってみたら2つめが、"a,b"と表示されました。 なお、単にCSVといってもソフトによって保存形式が違うんですね。 a a,b "a" "a,b" a,"b" "a","b" が、Windows版のExcel(95)では a,"a,b","""a""","""a,b""","a,""b""","""a"",""b""" となり三四郎8で保存すると、 "a","a,b",""a"",""a,b"","a,"b"",""a","b"" となりました。私の使いたいデータは桐の7で、これを「テキストで書き出す」とExcelと同じになりました。
K's K 1999/08/11(水) 01:44:25 上の3行目が、書いている間は離れていたのですが送信するとくっついて見づらくなってしまいました。 a a,b "a" "a,b" a,"b" "a","b" の6つです。 Aurai 1999/08/11(水) 05:28:49 長くなってしまいましたが $x='a,"a,b","""a""","""a, b, and c"""'; while( $x =~ s/^([^,"]*|"(""|[^"])*"),// ) { $_ = $1; s/^"(.*)"$/$1/; s/""/"/g; print "$_\n"; } $x =~ s/^"(.*)"$/$1/; $x =~ s/""/"/g; print "$x\n"; こんなのどうでしょう K's K 1999/08/12(木) 01:05:06 Auraiさん、ありがとうございます。目的のデータ517行分うまく切り出せました。 しかしPerlってすごいですね。バッチファイルぐらいしか知らない私でも根幹部分を教えてもらえれば、CSVからHTMLのテーブルに変換するプログラムが作れてしまう。あ、もちろん参考にするプログラムがあったからできたことですが・・・。 感動というかあきれています。 なお、桐の「テキストで書き出す」データはExcelのCSVと微妙に違っていました。 私と同じように桐のデータを利用する方は、一旦Excelを通して下さい。 Excelなんか持っていないという人もいらっしゃるでしょうね。 a"b"cというデータを桐はa"b"c、Excelは"a""b""c"に変換します。 ありがとうございました。 TwnLounge Ver2.06
|
ドキュメンタリータッチで全文引用した私であった。(要約するのが面倒という説もある)
読んでいただければ分かるが、CSVとはソフトによって処理が統一されていない、へんてこりんな形式なのであった。
第4章:後日談
Excel の95をインストールしているのである。Excel 97をアンインストールしてExcel 95をインストールしたのである。すると・・・・。
IEで「CSVファイルを表示させる」をクリックすると、ダウンロードの問い合わせが出る。あちゃ。
CSVファイルとは、(少なくとも私のマシンでは)、ネスケでは画面表示、IEとExcel95ではダウンロード、IEとExcel97ではExcelを呼び出して画面表示という、なんとも面妖な動きをするファイルであった。
第5章:かくして私はフリーソフト作家になった
ま、鉄面皮。鉄面皮。
CSV→HTMLtable変換Perlプログラムをダウンロードする
(csv_table.lzh 3KB)
ソフト2種類入ってます。
csv_table.cgi はブラウザで表示させて使います。PerlおよびCGIが生きている環境が必要です。
jcode.plが別途必要です。(データベースのlzhに入ってます)(ディフォルトでは同一ディレクトリに置く)
CSV→HTMLテーブル自動変換
|
という画面が出ます。元のファイルの拡張子はCSVである必要があります。
ディレクトリを指定すれば、別に同一ディレクトリになくてもOKのはずですが、チェックしてません。
指定されたファイルがCSV形式かどうかという判定など高級なことはしていません。
Excel形式のCSV対応ですので、桐、三四郎のCSVに関しては、データ内にコンマ、ダブルクオーテーションマークが含まれている場合エラーが出る可能性があります。1-2-3の形式は調べていないので分かりません。
例によって無保証です。(こんなん書いてみたかったのよね〜。)
fctt.pl はコマンドラインで使います。from csv to table の fcttです。
Windowsのドス窓では
perl fctt.pl filename + return
で使います。これも拡張子はcsvに固定してます。こちらはタイトル名は不可です。ファイル名と同じタイトルになります。よってjcode.plは不要です。
ただperl fctt.pl なら
Usage: fctt.pl filename without extentions
convert csv to html table
と、表示されます。
こちらの方は、PerlさえあればOKです。Mscの場合は分かりませんが、fctt.plを呼び出す際に、ファイルネームを渡す手段があれば原理的には動くはずですが。。。。
どちらのプログラムも生成されるHTMLファイルは同一です。一番のウリは生成されるファイルが小さいこと。
音楽年表のcsvファイルは42KB、それを三四郎8でHTMLファイルに変換すると、314KB。私のプログラムでは94KBです。
あと、少々のHTMLとPerlの知識があると、自分の好きなようにアレンジ出来ます。
追記:ということでデータベースをマイナーチェンジしてますので、よろしければ再ダウンロードしてみて下さい。