こんにちは、三流プログラマーのKen3です。 今回は、 ADOのCSV接続の自動で決まってしまうデータの型について少々。 でも、解決しなかったり・・・ いつもの三流的なアプローチなので、実際はアレンジして使ってください。 ※一部でも参考になればいいんだけど・・・/* * 1.今回のキッカケ */
No.080 Microsoft Text Driver (*.txt; *.csv) で接続してみた http://www.ken3.org/asp/backno/asp080.html から >質問なのですがcsvファイルを接続し、データを吸い上げたときに >IPアドレスのように111.222.333.444といった物が111.222333444とな >って上がってきてしまいました。吸い上げた時点で既にそのような形 >式になっていましたのでどうした物かと困っています。掲示板のログ と、質問をもらった。/* * 2.テストデータを作成してテストしてみる */
オバケが出たと言われたら、 そんなことないだろ、見間違いだろ と 言うのだが、現実に現象が発生するのか? コンピュータの場合は確認しやすい。 なぜ?確認しやすいかって? それは、同じデータを流して、何度も検証できるからかなぁ。 オバケの発生条件を教えてもらったので、 私もテストデータを作成して、見物してみることにした。 作成したCSVファイルは、ヘッダー付きで下記のように作成した。 http://www.ken3.org/cgi-bin/test/test101.csv 日付,IP,URL,分数TEST,少数TEST,備考,予備 2004/12/25,192.168.0.1,ken3.org,1/20,1.25,備考の文字,1-2-3 2005-01-08,192.168.0.25,/asp/,1/3,5.10,日付の形式を少し変えた 2005/01/19 17:30,192.168.0.17,vba,2/7,5,時刻を付けた,04-05-06 まだまだ、テストデータとして、足りないけど、↑手抜きでこんな感じ。 ※カンマと小数点が見難いが・・・ ADOでCSVの接続は、 'SQLのテーブル名には、ファイル名を指定します。 strSQL = "select * from test101.csv" '接続情報の作成 ドライバーの指定と、DBQには、パスのみを指定する Con = "Driver={Microsoft Text Driver (*.txt; *.csv)};DBQ=" & _ Server.MapPath(".") & ";" '↑MapPathに(".")を渡し、カレントディレクトリを渡す こんな感じで普通に接続のテストを行ってみます。 http://www.ken3.org/cgi-bin/test/test101-1.asp ↑実行テスト ↓実行結果 日付 IP URL 分数TEST 少数TEST 備考 予備 2004/12/25 192.168 ken3.org 1/20 1.25 備考の文字 2001/02/03 2005/01/08 192.168 /asp/ 1/3 5.1 日付の形式を少し変えた 2005/01/19 17:30:00 192.168 vba 2/7 5 時刻を付けた 2004/05/06 ホントだ、出たよ、不具合が・・・ ※だから読者が質問してきたんだろ読者が・・・/* * 3.テストデータから不具合のパターンを分析してみる */
結果が出たので分析してみます。 192.168.0.1 や 192.168.0.25 、 192.168.0.17 が、 192.168 と、なってしまった。 ここは、純粋に文字列で扱ってほしかったのに・・・ 次に、小数点付きの数値をテストしてみると、 1.25 5.10 5 は、5.1となっているので、数値扱いされている。 頭に戻って日付、 2004/12/25 と 2005-01-08 どちらも、日付と認識されるのか、 2005-01-08が2005/01/08となった。 興味があるのが、年が無くて、月日だったら? 1/20は、変換して1月20日と見るのか、文字列の1/20と見るのか気になった。 1/20 1/3 2/7 は、大丈夫みたいだ。 とすると、あとは、2000年問題で流行った、yy-mm-dd形式は? そこで、 1-2-3 と 04-05-06をテストしてみた。 なんと、2001/02/03と2004/05/06と自動変換されていた。 原因を探っていくと、 CSVファイルには、フィールドの型情報が無いので、 先頭から数行のデータを使って、フィールドの型を判断していて、 文字列でそのまま扱ってほしいのに、 これは日付、これは小数点付き数値などと自動で決めてしまう。 チラッと頭の毛が金髪とみただけで、心の中まで見ないで、 不良と決め付けている大人みたい・・・ なんて冴えない話は置いといて、どうしましょう??? 参考資料: http://support.microsoft.com/default.aspx?scid=kb;ja;278973 >データ型 >Excel テーブルは、従来のデータベースとは異なり、列に直接データ型を指定 >する方法がありません。代わりに、列の中の一定数の行が OLE DB プロバイダ >によりスキャンされ、そのフィールドのデータ型が推測されます。スキャンさ >れる行数は、デフォルトでは 8 行ですが、接続文字列の拡張プロパティで、 >MAXSCANROWS 設定に 1 〜 16 の値を指定することでスキャンされる行数を >変更できます。 CSVの資料じゃないけど、8行スキャンして、データ型を決めているのかなぁ。/* * 4.原因がわかったら対策を立てるのでは? */
原因が頭だけ見た自動判断なら、頭に文字列のデータを置けばいいんじゃない? チラッと頭の毛が金髪とみただけで不良少年と決め付ける大人がいるんなら、 先頭が1人でも黒髪だったら、鼻ピアスヘソピアスもOKで通るのかな。 初めだけ猫かぶるじゃないけど、先頭行を完璧な文字列として扱うように細工すれば? いいんじゃないの? 先頭行に礼儀正しいダミー君、ダミーのデータを送り込むとか? えっ、そんなことするの・・・セコ。。。/* * 5.ダミーファイルを先頭で読むか(UNION ALL でつなげるか・・・) */
もし、可能なら、フィールドがひと目で見てわかる、 優等生軍団じゃなくて、ダミーのファイルを1つ作成します。 ファイル名 dummy101.csvなどで1行型決めをする http://www.ken3.org/cgi-bin/test/dummy101.csv 日付,IP,URL,分数TEST,少数TEST,備考,予備 2000/01/01,ABCDEFG,文字だよ,ここも文字,9.999,備考は文字,予備も文字列 上記を作成して、 select * from dummy101.csv UNION ALL select * from test101.csv とSQLを発行してみた↓。 http://www.ken3.org/cgi-bin/test/test101-2.asp が、 結果は、変わらなかった(笑) 修正構想は、崩れ去った・・・/* * 6. それならと思い、ADOでCSVに接続して .GetString を テストしてみた */
他に何か無いかなぁと探ってみて、 .GetString なんてメソッドをADOで発見した。 .GetString(StringFormat, NumRows, ColumnDelimiter, RowDelimiter, NullExpr) 戻り値 Recordset をバリアント型 (Variant) 変数 (BSTR) の文字列として返します。 単語だけ見ると Get String これって文字列だよな? .GetString(adClipString, 行数, 区切り文字, 行間の区切り, NULL時の代替) を指定できるので、 .GetString(adClipString, , vbTab, vbCrLf, vbNullString) と、 タブ区切り、CRLFで改行された文字列を指定してみた 期待に胸を膨らませ、テストしてみた。 http://www.ken3.org/cgi-bin/test/test101-3.asp ↑.GetStringをテストしてみた Response.Write "<PRE>" strDATA = rs.GetString(adClipString, , vbTab, vbCrLf, vbNullString) Response.Write strDATA '内容を表示する Response.Write "</PRE>" とするが、期待通りの結果は得られず。 ※データがタブと改行で区切られたので、 別の処理では何か使えるかもしれないメソッドですが、 期待した無変換では、無かったです。/* * 7.終わりの挨拶 </HTML> */
今回は、 ADOでCSV接続したときに、 192.168.0.1 が、 192.168 と なってしまう件を調査したのですが、解決しませんでした。 やはり、テキストファイルで開いて、 自分でSplit関数で分解するしか無いのかなぁ・・・ 奥が深いですよね。 今回も解決していないのですが、 何かの参考となれば幸いです。 ASP、VBScript勉強中の三流プログラマーのKen3でした。
ここまで、読んでいただきどうもです。目的の情報が見つかったか?少々心配しつつ、、、
感想や質問・要望・苦情など 三流君へメッセージを送る。
下記のフォームからメッセージを送ることができます。
[三流君(TOP ken3.org へ戻る)]
/ [ASPで遊ぶ、失敗する]
/ [ASP記事 バックナンバー目次]
まぁ、基本はデータの受け取りかなぁ。
・[Form等を使用したデータのやり取り]・・・ASPと言っても、HTMLの入力フォームからデータを受け取ります。POSTやGETでやりとりを押さえますか。
次は、データの入出力 で ADOを使った(ADOで接続) と SQLの解説を少々
・[ADOでMdbファイルを使う]・・・MDBと接続して、簡単な追加・更新・削除を行った。
・[ADOでExcelと接続してみた]・・・.xlsと接続してSQLを使ってみた。
・[ADOでCSVと接続してみた]・・・.CSV テキストを読み出した。※更新・削除はできません
広告:
DBが使えるので、あまり使用しないけど、普通のテキストファイル処理
・[テキストファイル処理]・・・ファイルを開いて、書き込む。1行読み込みなどを軽く
VBScriptでFormat関数が無いなど、微妙にVBAと違うけど
[VBScript関数関係の説明]・・・少し、処理を書いてみた。
[その他処理サンプル]・・・あまり良いサンプル作れなかったけど。。。
何かの参考となれば幸いです。
[三流君(TOP ken3.org へ戻る)]
/ [ASPで遊ぶ、失敗する]
/ [ASP記事 バックナンバー目次]