Excel VBA質問箱 IV

当質問箱は、有志のボランティア精神のおかげで成り立っています。
問題が解決したら、必ずお礼をしましょうね。
本サイトの基本方針をまとめました。こちら をご一読ください。

投稿種別の選択が必要です。ご注意ください。
迷惑投稿防止のため、URLの入力を制限しています。ご了承ください。


8842 / 13645 ツリー ←次へ | 前へ→

【30798】CSVファイルの取込について セブン 05/11/4(金) 21:03 質問[未読]
【30799】Re:CSVファイルの取込について かみちゃん 05/11/4(金) 21:32 発言[未読]
【30800】Re:CSVファイルの取込について セブン 05/11/4(金) 22:07 質問[未読]
【30801】Re:CSVファイルの取込について Kein 05/11/4(金) 22:28 回答[未読]
【30804】Re:CSVファイルの取込について ichinose 05/11/4(金) 22:39 発言[未読]
【30808】Re:CSVファイルの取込について Hirofumi 05/11/4(金) 23:23 回答[未読]
【30824】Re:CSVファイルの取込について セブン 05/11/5(土) 9:47 お礼[未読]

【30798】CSVファイルの取込について
質問  セブン E-MAIL  - 05/11/4(金) 21:03 -

引用なし
パスワード
   始めまして。
CSVファイル取り込みについて質問いたします。
CSVファイルをVBAで取り込むようにしました。

NOU.CSV
タイトル1,タイトル2,タイトル3,タイトル4
DATE1,DATE2,DATE3,DATE4,
DATE5,DATE6,DATE7,DATE8,

上記のCSVファイルでは問題なく取り込むことができましたが、
これから取り込もうとしているCSVファイルは

タイトル1,タイトル2,タイトル3,タイトル4DATE1,DATE2,DATE3,DATE4,
DATE5,DATE6,DATE7,DATE8,
というタイトル行とデータ1行目(2行目)が1行になっています。

EXCELで「開く」では問題なく読み込めるのですが、VBAではうまくいきません。
どのような方法があるのでしょうか。
皆さんのお知恵をお借りできればと思います。

参考までコードを記しておきます。

Sub データ取込()
Dim dat(200, 200) As String

'txtデ−タ取り込み
  i = 0
  Open fname For Input As #1
Do Until EOF(1)
 For j = 0 To 165
  Input #1, dat(i, j)
  Cells(i + 1, j + 1) = dat(i, j)
Next
  On Error GoTo 0
   i = i + 1
Loop
Close #1
Range(Cells(1, 1), Cells(i, j)).Value = dat

【30799】Re:CSVファイルの取込について
発言  かみちゃん  - 05/11/4(金) 21:32 -

引用なし
パスワード
   こんにちは。かみちゃん です。

>EXCELで「開く」では問題なく読み込めるのですが、VBAではうまくいきません。
>どのような方法があるのでしょうか。

Input # ステートメントを使っていますが、
とりあえず、ふつうにCSVを読み込んではいけませんか?
(「マクロの記録」で記録できます)
そのあとに、1行目の次の行に行挿入して、1行目からDATE1,DATE2,DATE3,DATE4
を行挿入した行に移動すればいいのではないでしょうか?

【30800】Re:CSVファイルの取込について
質問  セブン E-MAIL  - 05/11/4(金) 22:07 -

引用なし
パスワード
   かみちゃんさんありがとうございます。
それで開くことができましたが、そのデータを既に開いている
シートに貼り付けたいのです。

既に開いているファイルでマクロを実行し
Cells(i + 1, j + 1) = dat(i, j)
で配列に配置し
Range(Cells(1, 1), Cells(i, j)).Value = dat
で開いているシートに貼り付けます。

上記の方法では、CSVファイルを読み込んだ時点で、
ファイルが開いてしまいます。

せっかくお答えいただいたのに申し訳ありません。
他の方法があればよろしくお願いします。

【30801】Re:CSVファイルの取込について
回答  Kein  - 05/11/4(金) 22:28 -

引用なし
パスワード
   1行目のみ、タイトルとデータを分離すれば良いのでしょーか ?
それなら

Sub データ取込()
  Dim i As Long, j As Long
  Dim Ary As Variant
  Dim Buf As String
  Const fname As String "C:\Temp\Test.csv"
  '↑適当に変更して下さい。

  i = 1
  Open fname For Input Access Read As #1
  Do Until EOF(1)
   Line Input #1, Buf
   Ary = Split(Buf, ",")
   If i = 1 Then
     For j = 0 To 3
      Cells(1, j + 1).Value = Ary(j)
     Next j
     For j = 4 To 11
      Cells(2, j + 1).Value = Ary(j)
     Next j
     i = i + 2
   Else
     Cells(i, 1).Resize(, UBound(Ary) + 1).Value = Ary
     i = i + 1
   End If
   Erase Ary
  Loop
  Close #1
End Sub

で、どうかな ?

【30804】Re:CSVファイルの取込について
発言  ichinose  - 05/11/4(金) 22:39 -

引用なし
パスワード
   セブン さん、みなさん、こんばんは。
>
>
>タイトル1,タイトル2,タイトル3,タイトル4DATE1,DATE2,DATE3,DATE4,
実はこれ↑タイトル4とDATE1の間には、表示されないコードがあるのでは
ありませんか?例えば、VbcrコードとかVblfコードとか

そうだと仮定すると・・・、


Sub testread()
  Dim dat1 As Variant
  Dim rw As Long
  Dim myarray As Variant
  Dim partarray As Variant
  Open "d:\csvtest.csv" For Input As #1
'       ↑これは、実際のファイルを指定して下さい
  rw = 1
  Do Until EOF(1)
    Line Input #1, dat1
    myarray = Split(dat1, vbLf)
    For idx = LBound(myarray) To UBound(myarray)
     partarray = Split(myarray(idx), ",")
     Range(Cells(rw, 1), Cells(rw, UBound(partarray) - LBound(partarray) + 1)).Value = partarray
     rw = rw + 1
     Next idx
    Loop
  Close #1
End Sub

【30808】Re:CSVファイルの取込について
回答  Hirofumi  - 05/11/4(金) 23:23 -

引用なし
パスワード
   もし、HeaderとDataの間にCrlf以外の改行コードが有るとしたら
Crの場合、Openステートメントが改行と見なすので、
Lfが改行コードに成って居るのでは?
だとすると、FileSystemObjectで読めるのでは?

Option Explicit

Public Sub ReadCsvFSO()

  Dim i As Long
  Dim vntFileName As Variant
  Dim wksResult As Range
  Dim lngRow As Long
  Dim lngColumn As Long
  Dim strProm As String
  
  '読み込むファイルを指定
  If Not GetReadFile(vntFileName, ThisWorkbook.Path) Then
    strProm = "読み込みがキャンセルされました"
    GoTo Wayout
  End If
  
  '画面更新を停止
  Application.ScreenUpdating = False
  
  '書き込むシートを設定
  Set wksResult = ActiveSheet
  '書き込み始める行位置を設定
  lngRow = 1
  '書き込み始める列位置を設定
  lngColumn = 1
  
  '読み込みファイルのデータをシートに出力
  '第1引数 読み込みファイル名
  '第2引数 書き込むシート
  '第3引数 書き込み始める行位置
  '第4引数 書き込み始める列位置
  CSVReadFSO vntFileName, wksResult, lngRow, lngColumn, True, ","
  
  strProm = "処理が完了しました"
  
Wayout:
  
  '画面更新を再開
  Application.ScreenUpdating = True
  
  Set wksResult = Nothing
  
  MsgBox strProm, vbInformation
  
End Sub

Private Sub CSVReadFSO(ByVal strFileName As String, _
              ByVal wksWrite As Worksheet, _
              Optional ByRef lngRow As Long = 1, _
              Optional ByRef lngCol As Long = 1, _
              Optional ByRef blnHeader As Boolean = True, _
              Optional strDelim As String = ",")
  
'  CSVデータの読み込み

  Dim vntField As Variant
  Dim strLine As String
  Dim blnMulti As Boolean
  Dim strRec As String
  Dim objFso As Object
  Dim objFileStr As Object
  Const ForReading = 1
  
  'FSOのオブジェクトを取得
  Set objFso = CreateObject("Scripting.FileSystemObject")
  '指定ファイルを読み込みモードでOpen
  Set objFileStr = objFso.OpenTextFile(strFileName, ForReading)
  
  With objFileStr
    Do Until .AtEndOfStream
      'ファイルから1行読み込み
      strLine = .ReadLine
      '読み込み行を論理レコードに追加
      strRec = strRec & strLine
      'CSVをフィールドに分割
      vntField = SplitCsv(strRec, strDelim, , , blnMulti)
      'もし、論理レコードに成らない場合
      If blnMulti Then
        '論理レコードにLfを追加
        strRec = strRec & vbLf
      Else
        If blnHeader Then
          '指定シートの指定行列位置について
          With wksWrite.Cells(lngRow, lngCol)
            'フィールドの書き込み
            .Resize(, UBound(vntField) + 1).Value = vntField
          End With
          '書き込み行位置を更新
          lngRow = lngRow + 1
        End If
        '論理レコードを初期化
        strRec = ""
        blnHeader = True
      End If
    Loop
    'ファイルをClose
    .Close
  End With
  
  Set objFileStr = Nothing
  Set objFso = Nothing
  
End Sub

Private Function SplitCsv(ByVal strLine As String, _
            Optional strDelimiter As String = ",", _
            Optional strQuote As String = """", _
            Optional strRet As String = vbCrLf, _
            Optional blnMulti As Boolean) As Variant

'      strLine     :分割元と成る文字列
'      strDelimiter  :区切り文字
'      SplitCsv    :戻り値、切り出された文字配列

  Dim lngDPos As Long
  Dim vntData() As Variant
  Dim lngStart As Long
  Dim i As Long
  Dim vntField As Variant
  Dim lngLength As Long
  
  i = 0
  lngStart = 1
  lngLength = Len(strLine)
  blnMulti = False
  Do
    ReDim Preserve vntData(i)
    If Mid$(strLine, lngStart, 1) <> strQuote Then
      lngDPos = InStr(lngStart, strLine, _
            strDelimiter, vbBinaryCompare)
      If lngDPos > 0 Then
        vntField = Mid$(strLine, lngStart, _
                  lngDPos - lngStart)
        If lngDPos = lngLength Then
          ReDim Preserve vntData(i + 1)
        End If
        lngStart = lngDPos + 1
      Else
        vntField = Mid$(strLine, lngStart)
        lngStart = lngLength + 1
      End If
    Else
      lngStart = lngStart + 1
      Do
        lngDPos = InStr(lngStart, strLine, _
                strQuote, vbBinaryCompare)
        If lngDPos > 0 Then
          vntField = vntField & Mid$(strLine, _
                lngStart, lngDPos - lngStart)
          lngStart = lngDPos + 1
          Select Case Mid$(strLine, lngStart, 1)
            Case ""
              Exit Do
            Case strDelimiter
              lngStart = lngStart + 1
              Exit Do
            Case strQuote
              lngStart = lngStart + 1
              vntField = vntField & strQuote
          End Select
        Else
          blnMulti = True
          vntField = Mid$(strLine, lngStart) & strRet
          lngStart = lngLength + 1
          Exit Do
        End If
      Loop
    End If
    vntData(i) = vntField
    vntField = Empty
    i = i + 1
  Loop Until lngLength < lngStart
  
  SplitCsv = vntData()
  
End Function

Private Function GetReadFile(vntFileNames As Variant, _
            Optional strFilePath As String, _
            Optional blnMultiSel As Boolean _
                    = False) As Boolean

  Dim strFilter As String
  
  'フィルタ文字列を作成
  strFilter = "CSV File (*.csv),*.csv," _
        & "Text File (*.txt),*.txt," _
        & "CSV and Text (*.csv; *.txt),*.csv;*.txt," _
        & "全て (*.*),*.*"
  '読み込むファイルの有るフォルダを指定
  If strFilePath <> "" Then
    'ファイルを開くダイアログ表示ホルダに移動
    ChDrive Left(strFilePath, 1)
    ChDir strFilePath
  End If
  'もし、ディフォルトのファイル名が有る場合
  If vntFileNames <> "" Then
    SendKeys vntFileNames & "{TAB}", False
  End If
  '「ファイルを開く」ダイアログを表示
  vntFileNames _
      = Application.GetOpenFilename(strFilter, 1, , , blnMultiSel)
  If VarType(vntFileNames) = vbBoolean Then
    Exit Function
  End If
  
  GetReadFile = True
  
End Function

【30824】Re:CSVファイルの取込について
お礼  セブン E-MAIL  - 05/11/5(土) 9:47 -

引用なし
パスワード
   ichinose さん、ありがとうございました。
おかげさまでできました。
かみちゃんさん、Keinさん、Hirofumiさん、ありがとうございました。
他の方のご意見もたいへん参考になりました。
これからも何かありましたら質問させていただきます。

8842 / 13645 ツリー ←次へ | 前へ→
ページ:  ┃  記事番号:
2610219
(SS)C-BOARD v3.8 is Free