[ 初めての方へ | 一覧(最新更新順) | 全文検索 | 過去ログ ]
『CSVから特定の列を抜き出す・・・2』(ちはる)
度々申し訳ありません。
[[20171014125556]]で質問させていただいた者です。
回答を下さった方のアドバイスや自分でも調べてみて、コードを書いてみたのですが、目的の物が出来あがらず、厚かましくも、もう一度質問をさせていただきます。
まず、目的なのですが、
同じ階層に、約100程のフォルダの中にそれぞれ5つ前後のCSVが格納されています。
そのCSVファイルの中から、特定の列のデータだけを管理用エクセルへ書き出す作業をします。
CSVデータの形式は全て共通、100列(固定)100〜200行(これは各々まちまち)程で、抜き出したい列は5つです。(2、5,8,9,17行目。ただし今後変更や、増えるかもしれません)
管理票エクセルシートに転記する際、データを昇順したり、特定のものだけを抜き出し、チェックしながら管理票エクセルに貼り付けて行くといった作業が必要になる為、CSVファイルのままではなく、エクセルに変換したいのです。
また、元のCSVファイルは、別の作業で統合や加工を行う必要がある為、変更を加えずそのままにしておきたいのです。
やりたい手順としては、
?@任意のCSVファイルを選択する(実行ボタンを押したらファイルパスを入力する画面が出て、入力をしてエンターを押したら以下?A〜?Cのアクションが起こるようにしたい)
?AそのCSVファイルから特定の列だけ抜き出す(2、5,8,9,17)など
?B特定の列のみなったCSVファイルをエクセルに変換し、元となったCSVファイルと同じフォルダに格納する(元となったCSVファイルは何も変更をせずそのまま閉じる)
?C出来れば元となったCSVファイルを閉じたあと、特定列だけ抜き出しエクセルに変換されたファイルが自動で開くようにしたい
調べてみて、一番目的に近かったのが以下の物なのですが・・・
Sub sample()
Dim file As String
Dim c As Integer
file = Application.GetOpenFilename("CSVファイル,*.csv?")
If file = "False" Then Exit Sub
Workbooks.Open file
c = InputBox("何列")
Workbooks.Open file
Columns(c).Delete
ActiveWorkbook.Close True
End Sub
これですと、まず
?@削除したい列が1つしか選べない
?ACSVからエクセルに変換という目的が出来ない
?B元のCSVを加工するコードになってしまう
ので、目的に適いません。
元になるCSVを予めコピーしておき、コピーで作業を行うという手もあるのですが、作業量が多い為現実的ではありませんし、別の作業で元のCSVを選択する際、間違ってしまう可能性もあるので、エクセル形式で吐き出させたいのです。
図々しい質問、お願いであり、誠に恥ずかしい限りなのですが、どのようにすれば上記目的な叶うのか、ご教示いだけないでしょうか。
どうぞよろしくお願いいたします。
< 使用 Excel:Excel2013、使用 OS:Windows10 >
?@
?A
?B
はそれぞれ、
1
2
3
と、丸つきで記述したものです。
お目汚しで申し訳ありませんでした。
(ちはる) 2017/10/14(土) 17:44
どうぞよろしくお願いいたします。
(ちはる) 2017/10/14(土) 17:49
csvファイルの1行目は列項目(フィールド名)になっていますか? 出来れば、一行目から数行抜粋して提示してもらえますか?
(seiya) 2017/10/14(土) 18:38
カナ 局名 県 住所 通称 番地 連番 規模 通名 待ち 人数
ティーケ TK 千葉 香住 かすみ 1-2 024 JJ TD 87 90
オオム OM 大阪 赤穂 アコ 8-9 345 NS IK 09 78
というようなCSVファイルです。
コメントして下さり、ありがとうございます。
もしよろしけばお教えください。
(ちはる) 2017/10/14(土) 18:56
区切り文字はカンマでは無いようですが、なんですか? (seiya) 2017/10/14(土) 19:04
エクセルから貼り付けたのですね、わかりました。
ユーザーフォームを使用して、フィールド選択をします。 http://news.mynavi.jp/articles/2009/08/24/vba/ 分らなければ上記リンク等を参考にしてください。
1) UserForm(UserForm1)を挿入して ListBox(ListBox1) と CommandButton(CommandButton1) を配置する。
2) UserFormを右クリックして [コードの表示] 出てきた画面の右空白部分に下記コードを貼り付ける。 もし既に何か書かれてあったら、一旦すべて削除してください。
Option Explicit Private ListTxt As String
Public Property Get Value() As String Value = ListTxt End Property
Private Sub UserForm_Initialize() Me.ListBox1.MultiSelect = 1 End Sub
Private Sub CommandButton1_Click() Dim i As Long ListTxt = "" With Me.ListBox1 For i = 0 To .ListCount - 1 If .Selected(i) Then ListTxt = ListTxt & "`, `" & .List(i) Next End With If Len(ListTxt) Then ListTxt = Mid$(ListTxt, 3) & "` " Me.Hide End Sub
3) 標準モジュールに下記コードを貼り付ける
Option Explicit
Sub test() Dim fn As String, myDir As String, txt As String Dim cn As Object, rs As Object, i As Long fn = Application.GetOpenFilename("CSVファイル,*.csv") myDir = Left$(fn, InStrRev(fn, "\")) fn = Mid$(fn, InStrRev(fn, "\") + 1) If fn = "False" Then Exit Sub Set cn = CreateObject("ADODB.Connection") Set rs = CreateObject("ADODB.Recordset") With cn .Provider = "Microsoft.ACE.OLEDB.12.0" .Properties("Extended Properties") = "Text;HDR=Yes;IMEX=1;FMT=CSVDelimited" .Open CreateObject("WScript.Shell").SpecialFolders("desktop") End With rs.Open "select * from `" & fn & "`", cn, 3 For i = 0 To rs.Fields.Count - 1 UserForm1.ListBox1.AddItem rs.Fields(i).Name Next UserForm1.Show rs.Close txt = UserForm1.Value If Len(txt) Then rs.Open "select " & txt & " from `" & fn & "`", cn, 3 With Sheets.Add For i = 0 To rs.Fields.Count - 1 .Cells(1, i + 1).Value = rs.Fields(i).Name Next .[a2].CopyFromRecordset rs .Name = fn .Copy With ActiveWorkbook .SaveAs myDir & Replace(fn, ".csv", ".xlsx") .Close False End With Application.DisplayAlerts = False .Delete Application.DisplayAlerts = True End With End If Unload UserForm1 Set cn = Nothing: Set rs = Nothing End Sub
これでtestを実行してみてください。 (seiya) 2017/10/14(土) 19:16 修正: 19:36
コードを若干変更しました。 (seiya) 2017/10/14(土) 19:37
残念だけど一生そうやってるしかないね... (seiya) 2017/10/14(土) 20:07
100列のなかのきまった5列を取り出すなら、
普通に開いて、その5列だけコピーして、元のCSVはそのまま閉じるだけですね。
余り難しく考えずに、できるところから、順を追って作っていけばよいでしょう。
一足飛びに完成品を求めるのは、気持ちはわかるが、決してあなたの為にもならない、と思います。
まずは、ひとつのCSVファイルを対象にして、以下のマクロ記録をとってみては?
・ひとつのCSVファイルを開く。
・新しいブックを開く
・5個の列をそれぞれコピーする
・ブックを保存する
・開いたCSVを閉じる
# マクロ記録を取ってください、といわれたら、
# こんなものが採れました、くらいの反応をしてもらえると期待していたが、
# 100列でしたでは、がっくりですよ。マクロ記録したくない、という意思表示ですよね。
# それと、毎回毎回手作業で指定してくれとは言っていない、マクロ記録の一回だけなんですがね。
# 勘違いされているようです。
(γ) 2017/10/14(土) 20:42
すぐに完成品を求めてしまうのは、確かに私自身の勉強に全くならないと痛感をいたしました。
試しに簡単なマクロからやってみるというのは、早速先程からチャレンジしてみています。
やりたい作業を紙に書き出し、1つ1つ試しながら動かしてみています。
今、seiya様から教えていただいユーザーフォームを使って削除したい指定の列を入れている
マクロを書いてみている所です。
また、Y様から先に教えていただいたマクロ記録から、CSVを取りこんで列を消すマクロのコードを読んで
どういう記述になっているのか、1行づつ理解しています。
お二方からアドバイスしていただいた事、ご親切にしていただいた事はしっかりと活かしていきます。
貴重なお時間を頂いたこと、労力を割いていただい事を忘れません。
本当にありがとうございました。
(ちはる) 2017/10/14(土) 21:05
>今、seiya様から教えていただいユーザーフォームを使って削除したい指定の列を入れている >マクロを書いてみている所です。
ってことは、削除しない列を表示(元来のコード)は出来てるってこと? まるっきりの素人がそこまで書けるとは思えんけど。 (seiya) 2017/10/14(土) 21:20
[ 一覧(最新更新順) ]
YukiWiki 1.6.7 Copyright (C) 2000,2001 by Hiroshi Yuki.
Modified by kazu.