Excel VBA 質問スレッド №1960 (解決済)

お手柔らかにお願いします。

投稿者 : 初心者     投稿日時 : 2024/07/10(Wed) 14:15:16     OS : 未指定     EXCEL : 未指定
--------------------------------
Sub CSV読み込み練習()

    Dim Int_csvFileNum As Integer
    Dim Str_csvLine As String
    Dim Str_dataArray() As String
    Dim var_selectedFile As Variant
    Dim baseSheet As Worksheet
    Dim lastRow As Long
    Dim colNum As Long
    
    ' ベースシートを設定
    Set baseSheet = ThisWorkbook.Sheets("ベース")
    
    ' CSVファイルを選択するダイアログを表示し、選択されたファイルのパスを取得
    var_selectedFile = Application.GetOpenFilename("CSVファイル (*.csv), *.csv", , "CSVファイルを選択してください", , False)
    
    ' ユーザーがキャンセルボタンを押した場合は処理を終了
    If VarType(var_selectedFile) = vbBoolean And var_selectedFile = False Then
        Exit Sub
    End If
    
    ' 選択されたファイルを開く
    Int_csvFileNum = FreeFile
    Open var_selectedFile For Input As #Int_csvFileNum
    
    ' 最終行を取得(既存データの下に追記するため)
    lastRow = baseSheet.Cells(baseSheet.Rows.Count, 1).End(xlUp).Row + 1
    
    ' 1行目を読み飛ばす
    Line Input #Int_csvFileNum, Str_csvLine
    
    ' 残りの行を読み取り、シートに書き込む
    Do Until EOF(Int_csvFileNum)
        ' 行を読み取り、配列に格納
        Line Input #Int_csvFileNum, Str_csvLine
        Str_dataArray = Split(Str_csvLine, ",") ' CSVデータをカンマで分割して配列に格納
        
        ' 配列のデータをシートに書き込む
        For colNum = LBound(Str_dataArray) To UBound(Str_dataArray)
            ' 日付の場合は、書式を設定してから値を代入する
            If colNum = 2 Then ' C列の場合(0から始まるインデックスなので、2は実際の3列目に相当)
                baseSheet.Cells(lastRow, colNum + 1).NumberFormat = "yyyy/mm/dd;@" ' 「短い日付形式」に設定
                baseSheet.Cells(lastRow, colNum + 1).Value = CDate(Str_dataArray(colNum)) ' 日付を設定
            Else
                baseSheet.Cells(lastRow, colNum + 1).Value = Str_dataArray(colNum)
            End If
        Next colNum
        
        ' 次の行へ移動
        lastRow = lastRow + 1
    Loop
    
    ' ファイルを閉じる
    Close #Int_csvFileNum
    
    ' 列の幅を調整
    baseSheet.Cells.EntireColumn.AutoFit
    
    ' ベースシートをアクティブにする
    baseSheet.Activate

End Sub

--------------------------------

上記はCSVデータを転記するコードで、今1行ずつ読み取って転記する形になっています。
これを2次元配列という、もう少し高速なコードに修正したいのですが(データが多くなってしまうため)
どなたかご教示いただけませんでしょうかm(__)m 初心者のため、厳しいお言葉はお控えください。

スポンサーリンク
[返信 1] Re : お手柔らかにお願いします。
投稿者 : ごんぼほり     投稿日時 : 2024/07/10(Wed) 17:07:17
質問タイトルは、質問内容が端的にわかるようにしてください。
「お願いします」とか「質問です」みたいなタイトルばかりになると、不都合なので。
 
2次元配列を使うためには、行数・列数が分かってないと面倒です

    Sub sample()
       Dim FSO As Object
       Dim sBuf As Variant, NR As Long, NC As Long
       Dim buf() As Variant, linebuf() As String
       Set FSO = CreateObject("Scripting.FileSystemObject")
       sBuf = FSO.OpenTextFile("D:\test.csv", ForReading, False, TristateTrue).ReadAll
       sBuf = Split(sBuf, vbLf)
       NR = UBound(sBuf) - 1
       NC = UBound(Split(sBuf(0), ","))
       ReDim buf(1 To UBound(sBuf), 0 To NC)
       For i = 1 To NR
           linebuf = Split(sBuf(i), ",")
           For j = 0 To NC
               buf(i, j) = linebuf(j)
           Next
       Next
       Stop
       Cells(Rows.Count, "A").End(xlUp).Offset(1).Resize(NR, NC + 1).Value = buf
    End Sub

[返信 2] Re : お手柔らかにお願いします。
投稿者 : ごんぼほり     投稿日時 : 2024/07/10(Wed) 17:09:13
ReDim buf(1 To UBound(sBuf), 0 To NC)

ReDim buf(1 To NR, 0 To NC)

の間違いでした

[返信 3] Re : お手柔らかにお願いします。
投稿者 : てらてら     投稿日時 : 2024/07/10(Wed) 19:59:15
こんにちは。

ExcelVBAでは、CSVファイルを手元のシートにそのまま読み込む事が出来ます。

お目当てのシートにCSVファイルを読み込めば、配列を用意しなくてもOKです。
後は、読み込んだシートを整形すれば良いでしょう。

https://help-vba.com/readcsv/ より引用
Sub FileOpen_Click()
    Dim FileName As String
    FileName = Application.GetOpenFilename("CSVファイル,*.CSV")

    If FileName <> "False" Then

	    Dim ws As Worksheet
	    Set ws = Worksheets("ベース")     '読込むシートを指定
	    Application.ScreenUpdating = False
	    ws.Cells.Clear  'それまでのデータをクリアします。
	    Workbooks.Open FileName:=fn
	    ActiveSheet.Cells.Copy ws.Cells
	    ActiveWorkbook.Close SaveChanges:=False
	    Application.ScreenUpdating = True

    Else
        MsgBox "キャンセルしました。"
    End If
    MsgBox "終了しました。"
End Sub

[返信 4] Re : お手柔らかにお願いします。
投稿者 : tek     投稿日時 : 2024/07/11(Thu) 11:06:33
たぶん、クエリ テーブルによりテキスト ファイルをインポートする方法が一番早いと思います。
各プロパティはヘルプ(F1キー)で確認ください。
Sub CSV読み込み練習1()
    Dim var_selectedFile As String
    Dim baseSheet As Worksheet
    Dim lastR As Range
    
    ' ベースシートを設定
    Set baseSheet = ThisWorkbook.Sheets("ベース")
    
    ' CSVファイルを選択するダイアログを表示し、選択されたファイルのパスを取得
    var_selectedFile = Application.GetOpenFilename("CSVファイル , *.csv", , "CSVファイルを選択してください", , False)
    
    ' ユーザーがキャンセルボタンを押した場合は処理を終了
    If var_selectedFile = "False" Then Exit Sub
    
    With baseSheet
        ' 既存データの下セルを取得
        Set lastR = .Cells(.Rows.Count, 1).End(xlUp).Offset(1)
    
        ' 選択されたファイルをインポートする
        With .QueryTables.Add("TEXT;" & var_selectedFile, lastR)
            .AdjustColumnWidth = True                           ' 列の幅を調整
            .TextFilePlatform = 932                             ' テキスト形式要変更 932(S-JIS)
            .TextFileStartRow = 2                               ' 1行目を読み飛ばす
            .TextFileTextQualifier = xlTextQualifierDoubleQuote ' 引用符:"
            .TextFileCommaDelimiter = True                      ' カンマ区切り
            .TextFileColumnDataTypes = Array(1, 1, 5)           ' C列:YMD,他:標準
            .Refresh BackgroundQuery:=False
            .Delete
        End With
    
        .Range(lastR, lastR.End(xlDown)).Offset(, 2).NumberFormat = "yyyy/mm/dd;@"  ' 「短い日付形式」に設定
        ' ベースシートをアクティブにする
        .Activate
    End With
    
End Sub

[返信 5] Re : お手柔らかにお願いします。
投稿者 : 初心者     投稿日時 : 2024/07/12(Fri) 12:09:56
■[返信 4] tekさん(2024-07-11 11:06:33)の記事
> たぶん、クエリ テーブルによりテキスト ファイルをインポートする方法が一番早いと思います。
> 各プロパティはヘルプ(F1キー)で確認ください。
> Sub CSV読み込み練習1()
> Dim var_selectedFile As String
> Dim baseSheet As Worksheet
> Dim lastR As Range

> ' ベースシートを設定
> Set baseSheet = ThisWorkbook.Sheets("ベース")

> ' CSVファイルを選択するダイアログを表示し、選択されたファイルのパスを取得
> var_selectedFile = Application.GetOpenFilename("CSVファイル , *.csv", , "CSVファイルを選択してください", , False)

> ' ユーザーがキャンセルボタンを押した場合は処理を終了
> If var_selectedFile = "False" Then Exit Sub

> With baseSheet
> ' 既存データの下セルを取得
> Set lastR = .Cells(.Rows.Count, 1).End(xlUp).Offset(1)

> ' 選択されたファイルをインポートする
> With .QueryTables.Add("TEXT;" & var_selectedFile, lastR)
> .AdjustColumnWidth = True ' 列の幅を調整
> .TextFilePlatform = 932 ' テキスト形式要変更 932(S-JIS)
> .TextFileStartRow = 2 ' 1行目を読み飛ばす
> .TextFileTextQualifier = xlTextQualifierDoubleQuote ' 引用符:"
> .TextFileCommaDelimiter = True ' カンマ区切り
> .TextFileColumnDataTypes = Array(1, 1, 5) ' C列:YMD,他:標準
> .Refresh BackgroundQuery:=False
> .Delete
> End With

> .Range(lastR, lastR.End(xlDown)).Offset(, 2).NumberFormat = "yyyy/mm/dd;@" ' 「短い日付形式」に設定
> ' ベースシートをアクティブにする
> .Activate
> End With

> End Sub






ご回答いただきありがとうございます。
内容を確認し、実施してみます。
お時間いただきありがとうございました。

[返信 6] Re : お手柔らかにお願いします。
投稿者 : 通りすがり     投稿日時 : 2024/07/13(Sat) 12:40:47
今後のために書きます。

>内容を確認し、実施してみます。
確認してから解決済みにしてください。

また、回答いただいた方には、もれなく返事してください。
無視はヒドイね。初心者かどうかは関係なく、礼を欠いています。
あなたのために時間を費やしています。(むろん幾分かはご自分のためという部分はあるにせよ)
トライした結果をキチンと返すのが礼儀です。

それとタイトルは指摘が既にあったとおりです。
きちんと要約を書くようにしてください。

また必要も無いのに、全文引用はスペースの無駄です。

>初心者のため、厳しいお言葉はお控えください。
初心者などという甘えたHNはやめたほうがいいですよ。

当掲示板について
  • Excel VBA に関する掲示板です。Excel VBA に関する質問や疑問、それに対する解決方法など気軽に投稿してください。
  • 記事内ではHTMLのタグは使用できません。
  • 記事は一度投稿すると修正できません。内容を訂正したい場合は返信で対応してください。
  • Sub〜End Sub、Function〜End Function は自動的にプログラムコードとみなし、枠で囲って見やすくします。
  • Excel VBA とは関係ないことや、他人が不快に思うようなことなど、管理人が適当でないと判断した記事は削除する場合があります。
スポンサーリンク
返信入力フォーム
お 名 前  :
内  容   :

ステータス  :

認証コード  : キャプチャ画像 




( 処理日時 : 2025-07-03 16:44:48 )
タイトルとURLをコピーしました