【入門編】ADOのCursorTypeプロパティが及ぼす影響:動的カーソルと静的カーソルの実務的使い分け – Access VBA解析バイブル

スポンサーリンク
スポンサーリンク

「データの『鮮度』か、『速度』か」——ADO CursorTypeを掌握して、プロのAccess開発者へ

こんにちは。よくここまで辿り着きましたね。
マクロの記録から一歩踏み出し、「自分でコードを書きたい」と願うその向上心こそが、エンジニアとしての最初の、そして最も重要な資質です。

Access VBAを学んでいると、必ずと言っていいほど「DAO(ディー・エー・オー)」と「ADO(エー・ディー・オー)」という二つの言葉に出会います。
「どちらを使えばいいのか?」「なぜか動きが重い」「他の人が更新したデータが反映されない……」
そんな壁にぶつかっているあなたに、今日は「CursorType(カーソルタイプ)」という、データの見え方を決定づける極めて重要な概念を伝授します。

ここをクリアすれば、あなたの作るアプリケーションの品質は、一気に「ツール」から「プロのシステム」へと昇華するはずですよ。

1. そもそも、DAOとADOは何が違うのか?

本題に入る前に、まずは地図を手に入れましょう。DAOとADOの違いを理解していないと、コードの海で迷子になってしまいます。

  • DAO (Data Access Objects):

Accessの「ネイティブ」な技術です。Accessの内部構造に最適化されており、Accessファイル(.accdb)を操作するなら、もっとも高速で安定しています。いわば「地元に精通したベテラン」です。

  • ADO (ActiveX Data Objects):

Accessの外の世界(SQL ServerやOracle、Web APIなど)と通信するための「共通言語」です。データの種類を問わず、同じ書き方で操作できる柔軟性を持っています。いわば「世界中どこでも通用する外交官」です。

「Access内だけで完結するならDAO、外部のデータベースと連携するならADO」というのが基本戦略です。今回は、柔軟性の高いADOの挙動について深掘りしていきます。

2. 「カーソル」とは、データの「窓」である

ADOでデータを読み込むとき、私たちは「Recordset(レコードセット)」というオブジェクトを使います。このレコードセットが、データベースから取り出したデータの塊を指し示す「窓」のような役割を果たします。

この「窓」の性質を決めるのが、`CursorType` プロパティです。

イメージしてください。あなたは今、大きな図鑑(データベース)を読んでいます。

  • 静的カーソル (Static Cursor): 図鑑を開いた瞬間のページを「写真に撮って」眺めている状態。
  • 動的カーソル (Dynamic Cursor): 図鑑を「リアルタイムで直接」見ている状態。

この違いが、実務において致命的な差を生むのです。

3. CursorTypeの使い分け:速度か、鮮度か

実務でよく使う、代表的なカーソルタイプを比較してみましょう。

① 静的カーソル (`adOpenStatic`):スピード重視の「スナップショット」

データを開いた瞬間の状態をメモリ上にコピーして保持します。

  • メリット: 非常に高速。一度読み込めば、その後データベースがどう変わろうと、手元のデータは変わりません。
  • デメリット: 他のユーザーがデータを更新・追加しても、あなたの画面には反映されません(「鮮度」がない)。
  • 使い所: 集計処理、レポート作成、データの読み取り専用画面など。

② 動的カーソル (`adOpenDynamic`):リアルタイムの「ライブビュー」

データベースの現在の状態を常に追いかけます。

  • メリット: 他のユーザーが追加したレコードや、変更した内容が即座に反映されます(「鮮度」が最高)。
  • デメリット: 常に「最新はどうなっているか?」とデータベースに問い合わせ続けるため、動作が重くなります。また、ネットワーク負荷も高まります。
  • 使い所: 複数人が同時に同じデータを編集する、リアルタイム性が求められる管理画面など。

③ 前方専用カーソル (`adOpenForwardOnly`):最速の「一方向通行」

最初から最後まで、一度読み飛ばしたら戻れない、最も軽量なタイプです。

  • メリット: メモリ消費が最小限で、圧倒的に速い。
  • デメリット: 「前のレコードに戻る」といった操作ができません。
  • 使い所: 大量のデータを順番に処理して計算するだけのプログラムなど。

4. 【実践】CursorTypeを切り替えるVBAコード

では、実際にどのようにコードを書くのか見てみましょう。
以下のコードは、接続設定からカーソルタイプの指定までを網羅したテンプレートです。

Option Explicit

' ADOを使用するための参照設定が必要です:
' Microsoft ActiveX Data Objects x.x Library

Sub DemonstrateCursorTypes()
    Dim cn As ADODB.Connection
    Dim rs As ADODB.Recordset
    Dim strConn As String
    Dim strSQL As String
    
    ' 1. 接続文字列の設定 (Accessファイルに接続する例)
    ' ※ご自身の環境に合わせてパスを書き換えてください
    strConn = "Provider=Microsoft.ACE.OLEDB.12.0;Data Source=" & CurrentProject.FullName & ";"
    
    ' 2. SQL文の準備
    strSQL = "SELECT * FROM T_社員マスタ"
    
    On Error GoTo ErrorHandler
    
    ' Connectionオブジェクトの生成とオープン
    Set cn = New ADODB.Connection
    cn.Open strConn
    
    ' --- パターンA: 静的カーソル (adOpenStatic) ---
    ' 処理速度を優先し、読み取り専用に近い形でデータを扱う場合
    Set rs = New ADODB.Recordset
    rs.CursorType = adOpenStatic ' ★ここがポイント!
    rs.LockType = adLockOptimistic ' 更新を許可する設定
    
    Debug.Print "--- 静的カーソルでオープン ---"
    rs.Open strSQL, cn
    
    If Not rs.EOF Then
        Debug.Print "現在の社員名: " & rs!社員名
    End If
    
    ' 読み込みが終わったら閉じる
    rs.Close
    Set rs = Nothing
    
    
    ' --- パターンB: 動的カーソル (adOpenDynamic) ---
    ' 他者の更新をリアルタイムに反映させたい、インタラクティブな操作の場合
    Set rs = New ADODB.Recordset
    rs.CursorType = adOpenDynamic ' ★ここがポイント!
    rs.LockType = adLockOptimistic
    
    Debug.Print "--- 動的カーソルでオープン ---"
    rs.Open strSQL, cn
    
    ' (ここで他のユーザーがデータを書き換えると、rs.Requery等で反映される)
    
    If Not rs.EOF Then
        Debug.Print "現在の社員名(ライブ): " & rs!社員名
    End If
    
    ' クリーンアップ
    rs.Close
    Set rs = Nothing
    cn.Close
    Set cn = Nothing
    
    MsgBox "処理が正常に完了しました。", vbInformation
    Exit Sub

ErrorHandler:
    MsgBox "エラーが発生しました: " & Err.Description, vbCritical
    If Not rs Is Nothing Then If rs.State = adStateOpen Then rs.Close
    If Not cn Is Nothing Then If cn.State = adStateOpen Then cn.Close
    Set rs = Nothing
    Set cn = Nothing
End Sub

コードの解説と陥りやすい罠

1. `rs.CursorType` の指定: ここで `adOpenStatic` か `adOpenDynamic` を選ぶことで、プログラムの挙動が劇的に変わります。
2. `rs.LockType`(ロックタイプ): カーソルタイプとセットで考えましょう。`adLockOptimistic`(楽観的ロック)は、「編集が終わるまでは他の人に邪魔させないけれど、書き込む瞬間だけロックをかける」という、現代的な効率の良いやり方です。
3. エラーハンドリング: データベース操作は、ネットワーク断絶やファイルロックなど、予期せぬエラーがつきものです。必ず `On Error GoTo` で、エラー時に `Connection` や `Recordset` を適切に閉じる(`Close` する)処理を書いてください。これを怠ると、「Accessがファイルを開いたままになっていて、他の人が開けない!」というトラブルの原因になります。

5. アーキテクトからのアドバイス:迷った時の指針

「結局、どっちを使えばいいの?」と迷ったら、この基準に従ってください。

  • 「計算して、結果を出して、終わり」の処理なら

👉 `adOpenStatic`(または `adOpenForwardOnly`)を選んでください。無駄な通信を減らし、ユーザーを待たせないのがプロの仕事です。

  • 「画面を開いたまま、誰かが更新したのをパッと見せたい」なら

👉 `adOpenDynamic` を検討してください。ただし、データ量が多い場合は、動作がガタガタになるリスクを覚悟し、必要最小限の範囲に絞って使用しましょう。

おわりに

CursorTypeの使い分けを理解することは、単なる文法の習得ではありません。「データの性質を理解し、システムのリソース(メモリや通信)をどう配分するか」という、設計思想に触れることなのです。

最初は難しく感じるかもしれません。でも、実際にコードを書いて、動作の重さの違いを肌で感じてみてください。その経験こそが、あなたを「マクロ使い」から「真のエンジニア」へと変えてくれます。

ここをクリアすれば、Access VBAの基本はバッチリですよ。
次の一歩へ、自信を持って進んでくださいね。応援しています!

タイトルとURLをコピーしました