項目

固定長ファイルの読込み

概要

バイナリで読み込み、CopyMemory構造体配列にコピーしています。

Option Compare Database
Option Explicit

'【固定長ファイルの仕様】
'-----------+------------+------+------+------+
'  項目名   |    属性    | 桁数 | 開始 | 終了 |
'-----------+------------+------+------+------+
'   ID     |  X(3)      |   3  |    1 |    3 |
'-----------+------------+------+------+------+
'   商品名  |  X(10)     |  10  |    4 |   13 |
'-----------+------------+------+------+------+
'   数量    | -9(4).9(2) |   8  |   14 |   21 |
'-----------+------------+------+------+------+
'   単価    |  9(5)      |   5  |   22 |   26 |
'-----------+------------+------+------+------+

'【テストデータ】test.txt
' 001商品1      0010.0001000
' 002item2     -0010.0000200
' 003ショウヒン3     0100.2500300

'--------------------------------------------------------------
' API宣言領域
'--------------------------------------------------------------
'メモリコピー
Public Declare Sub CopyMemory Lib "kernel32" Alias "RtlMoveMemory" _
        (Destination As Any, Source As Any, ByVal Length As Long)

'--------------------------------------------------------------
' 構造体定義領域
'--------------------------------------------------------------
Private Type testStructure
    ID(2) As Byte
    itemName(9) As Byte
    suryo(7) As Byte
    tanka(4) As Byte
End Type

'--------------------------------------------------------------
' 定数定義領域
'--------------------------------------------------------------
Private Const FIXED_FILE_ROW_LENGTH = 26

'--------------------------------------------------------
' 名称    : readFixedFile
'
' 機能    : 固定長ファイルの読込
'--------------------------------------------------------
Sub readFixedFile()

  Dim filePath    As String
  Dim fileNumber  As String
  Dim fileLength  As Long
  Dim byteBuf()   As Byte
  Dim strBuf      As String
  Dim table
  Dim rowData     As String
  
  '読み込むファイル
  filePath = "E:\temp\test.txt"
 
  '---------------------------------
  ' 固定長ファイルの読込
  '---------------------------------
  'ファイル長
  fileLength = FileLen(filePath)
  '領域割当
  ReDim byteBuf(fileLength - 1)
  'ファイルハンドル
  fileNumber = FreeFile
  'オープン
  Open filePath For Binary As #fileNumber
  'バイト配列へ読込
  Get #fileNumber, , byteBuf
  'クローズ
  Close #fileNumber

  '---------------------------------
  ' 配列に変換
  '---------------------------------
  strBuf = StrConv(byteBuf, vbUnicode)             'Byte→String
  table = Split(strBuf, vbCrLf, , vbBinaryCompare) '配列へ変換
  
  '---------------------------------
  ' 構造体配列に格納
  '---------------------------------
  Dim testStructureArray() As testStructure
  Dim index                As Long
  
  For index = 0 To UBound(table) - 1
  
    '行データ
    rowData = table(index)
    '値を保持しつつ再配置
    ReDim Preserve testStructureArray(index)
    'バイト配列初期化
    Erase byteBuf
    'Unicode → ShiftJis → byte配列
    byteBuf = StrConv(rowData, vbFromUnicode)
    'CopyMemoryで構造体にコピー
    CopyMemory testStructureArray(index), byteBuf(0), FIXED_FILE_ROW_LENGTH
    
  Next
  
  '---------------------------------
  ' 結果をイミディエイトウィンドウに出力
  '---------------------------------
  For index = 0 To UBound(testStructureArray)
    
    With testStructureArray(index)
    Debug.Print "【"; index + 1; "行目】"
    Debug.Print "ID      :"; StrConv(.ID, vbUnicode)
    Debug.Print "商品名  :"; StrConv(.itemName, vbUnicode)
    Debug.Print "数量    :"; Val(StrConv(.suryo, vbUnicode))
    Debug.Print "単価    :"; Val(StrConv(.tanka, vbUnicode))
    End With
    
  Next
  
    '【 1 行目】
    'ID      :001
    '商品名:  商品1
    '数量    : 10
    '単価    : 1000
    '【 2 行目】
    'ID      :002
    '商品名:  item2
    '数量    :-10
    '単価    : 200
    '【 3 行目】
    'ID      :003
    '商品名:  ショウヒン3
    '数量    : 100.25
    '単価    : 300

End Sub