Excel 2003 VBAでIteratorを実装する(書きかけ)
はじめに
Excel 2003のVBAでデータを配列に格納してExcelやCSVにデータを出力するというプログラムを書いていたのですが、配列の扱いが非常に面倒なので、Iteratorを実装してみました。
やりたいこと
- データのイメージとしては縦x横の表形式なので、それらのデータを格納できる変数を使用する
- 2次元配列を使うのはめんどいので、1セットのデータ(Excelでいう1行データ)をCollection変数に格納し、さらにそれを配列に格納する(Collection変数にCollection変数を格納できないので)
- データ数が不定で動的配列を使用したいが、配列の管理しなくて良いようにモジュール側で管理を行う
前提
中身
データを格納するクラスモジュール
クラス名: DataRowSet.cls
Option Explicit '############################################################################# ' まとまりのあるデータを行セット(例: オブジェクトの配列)として格納する ' ' @author satsv '############################################################################# Private DataRows() As Object ' データ格納用 Private Last As Integer ' 配列数 Private Sub Class_Initialize() Last = 0 End Sub '############################################################################# ' 指定したインデックスに格納してあるデータを取り出す ' ' @param index 配列のインデックス ' @return インデックスが指し示す要素 '############################################################################# Public Function Item(ByVal index As Integer) As Object Set Item = IIf(index < Last, DataRows(index), Nothing) End Function '############################################################################# ' データを配列に格納し、配列要素数を更新 ' ' @param objRecord データ '############################################################################# Public Sub Add(ByRef objRecord As Object) ReDim Preserve DataRows(Last) Set DataRows(Last) = objRecord Last = Last + 1 End Sub '############################################################################# ' 配列に格納されているデータ数を取得 ' ' @return 配列要素数 '############################################################################# Public Function GetLength() As Integer GetLength = Last End Function '############################################################################# ' Iteratorオブジェクトを生成し、自分自身を渡す ' ' @return Iteratorオブジェクト '############################################################################# Public Function Iterator() As Object Dim it As Object Set it = New DataRowSetIterator it.DataRowSet = Me Set Iterator = it End Function
Iteratorモジュール
クラス名: DataRowSetIterator.cls
Option Explicit '############################################################################# ' 行セット処理用Iterator ' ' @author satsv '############################################################################# Private RowSet As Object ' 行セット格納用 Private CurrentCursor As Integer ' 配列インデックス Private Sub Class_Initialize() CurrentCursor = 0 End Sub Private Sub Class_Terminate() Set RowSet = Nothing End Sub '############################################################################# ' プロパティ: 行セット格納用オブジェクトの設定(SetPropertyのみ) ' ' @return 行セット格納用オブジェクト '############################################################################# Public Property Let DataRowSet(ByRef Reference As Object) Set RowSet = Reference End Property '############################################################################# ' 次の要素があるかどうか ' ' @return 次の要素が存在すればTrue '############################################################################# Public Function HasNext() As Boolean HasNext = (CurrentCursor < RowSet.GetLength) End Function '############################################################################# ' 現在行(インデックスが指す要素)を返し、インデックスを次へ進める ' ' @return インデックスが指している要素 '############################################################################# Public Function GetNext() As Object Dim rec As Object Set rec = RowSet.Item(CurrentCursor) CurrentCursor = CurrentCursor + 1 Set GetNext = rec End Function Public Function HasPrevious() As Boolean End Function Public Function GetPrevious() As Object End Function