CopyFromRecordsetでヘッダー・列数・行数を指定する方法|Excel VBA実践例

5件3フィールドから見出しと先頭3件2列を出力

CopyFromRecordsetでExcelにデータを貼り付けると、列見出しが出なかったり、想定以上の件数が出力されたりすることがあります。これは使い方を整理すると解決できます。

ケンさん(SE)

データは貼れたのに、1行目に項目名がないんだ。

チャー

ヘッダーは別に書くにゃ。最大行数と列数も指定できるよ。

目次

CopyFromRecordsetはデータ本体だけをコピーする

CopyFromRecordsetはRecordsetのフィールド名を見出しとして自動転記しません。Fields(i).Nameを使い、ヘッダーを先に出力します。

見出し行を付けるVBAサンプル

以下は取得済みのRecordsetrsを使う抜粋です。事前に接続・SQL実行が完了しているものとします。

Dim ws As Worksheet
Dim dest As Range
Dim i As Long
Dim copied As Long

Set ws = ThisWorkbook.Worksheets("Sheet1")
For i = 0 To rs.Fields.Count - 1
    ws.Cells(1, i + 1).Value = rs.Fields(i).Name
Next i

Set dest = ws.Range("A2")
copied = dest.CopyFromRecordset(rs)
MsgBox copied & "件を出力しました"

ここでは、1行目に列名、2行目以降にデータを配置しています。戻り値のcopiedはコピーされたレコード数です。

MaxRows・MaxColumnsで最大件数と最大列数を指定

CopyFromRecordsetには省略可能な2つの引数があります。MaxRowsは最大レコード数、MaxColumnsは最大フィールド数です。

Set dest = Worksheets("Sheet1").Range("A2")
copied = dest.CopyFromRecordset(rs, 100, 3)

この例では最大100行×3列をコピーします。ただし、Recordsetに100件未満しか残っていなければ、残りの件数までしか転記されません。

列の並び替えはSQLで指定する

MaxColumns=3は好きな列を3つ選ぶ機能ではありません。Recordsetの先頭から3列を対象とします。必要なフィールドと並び順はSELECT句で決めましょう。

SELECT product_code, product_name, quantity
FROM sample_items
ORDER BY product_code

上のSQLは架空のテーブルに対する例です。SELECT *を避けて必要な列を明示すると、出力列の仕様が安定しやすくなります。行の順序も必要ならORDER BYを指定します。

行数制限とSQLでの絞り込みの違い

MaxRowsはExcelへコピーする最大レコード数を指定するもので、SQLの検索件数を減らすものではありません。データベースへの負荷や取得時間も抑えたい場合は、SQLのWHERE句などで取得対象そのものを絞り込みます。

出力前にチェックする項目

  • ヘッダーの項目数とRecordsetのフィールド数が合っているか
  • Excelの最終行・最終列からはみ出さないか
  • 前回の出力結果を消す必要があるか
  • 同じRecordsetを再利用する際、現在位置は適切か

【実行前・実行後】5件のデータから先頭3件・2列だけ表示する

5件3フィールドから見出しと先頭3件2列を出力
Windows版Excelでの実測値をもとにした図解(架空データ)

転記前のRecordsetは5件・3フィールドでした。CopyFromRecordset(rs, 3, 2)の戻り値は3で、見出しを含めてA1:B4に出力されました。5行目とC列は空欄でした。

元データ5件を、見出し付きのExcel表に最大3行×2列で出力する例です。データの件数と引数の対応を見比べてみましょう。

実行前:Recordsetにある5件・3フィールド(架空データ)

商品コード商品名数量
P001商品A10
P002商品B20
P003商品C15
P004商品D30
P005商品E12

VBAコード:先頭2フィールドのヘッダーを追加して3件だけ転記。次は外部DB接続を必要としないADOの検証用サンプルです。

Sub DemoHeaderAndLimit()
    Dim rs As Object, ws As Worksheet
    Dim dest As Range
    Dim i As Long, n As Long
    Dim names As Variant, qty As Variant

    names = Array("商品A", "商品B", "商品C", "商品D", "商品E")
    qty = Array(10, 20, 15, 30, 12)

    Set rs = CreateObject("ADODB.Recordset")
    rs.CursorLocation = 3 ' adUseClient
    rs.Fields.Append "商品コード", 202, 8
    rs.Fields.Append "商品名", 202, 30
    rs.Fields.Append "数量", 3
    rs.Open
    For i = 0 To 4
        rs.AddNew Array("商品コード", "商品名", "数量"), _
                  Array("P00" & (i + 1), names(i), qty(i))
    Next i
    rs.MoveFirst

    Set ws = ThisWorkbook.Worksheets.Add
    ws.Range("A1").Value = rs.Fields(0).Name
    ws.Range("B1").Value = rs.Fields(1).Name

    Set dest = ws.Range("A2")
    n = dest.CopyFromRecordset(rs, 3, 2)
    Debug.Print n & "件を転記しました"
    rs.Close
    Set rs = Nothing
End Sub

実行後:Excelにヘッダー+3行・2列を出力

Excelの行A列:商品コードB列:商品名
1商品コード商品名
2P001商品A
3P002商品B
4P003商品C

このようにCopyFromRecordset(rs, 3, 2)では最大3レコード・先頭2フィールドをコピーします。3行のデータにヘッダー1行が加わり、Excel上は合計4行になります。戻り値はVBAエディターのイミディエイトウィンドウ(Ctrl+G)で確認できます。

注意:ここでの3件は現在のレコード位置からの件数です。SQLで取得する件数を3件に減らす指定ではありません。また、先頭2列以外を選びたい場合はSELECT句の列順を変更してください。

検証環境はWindows版Excel 16.0(ビルド20527)とADOです。2026年11月8日に、外部データベースを使わず架空データで検証しました。

CopyFromRecordsetをもっと詳しく学びたい方へ

基本操作からエラー対策、データの取り込みや書式設定まで体系的に学びたい方には、Kindle書籍『Excel VBA CopyFromRecordset 実践ガイド』もおすすめです。

チャー

ぜひ、読んでみてニャ🐈

まとめ

ヘッダーはFields.Name、件数と列数は引数、列選択はSQLと役割を分けると、意図した表を作りやすくなります。

関連記事・もっと詳しく学ぶには

基本から確認したい方は、CopyFromRecordsetの使い方完全ガイドをご覧ください。
高速化の背景はCopyFromRecordsetはなぜ速い?で解説しています。

参考資料:Microsoft Learn:Range.CopyFromRecordset メソッド(確認日:2026年11月8日)。コード例は架空データ・一般的な環境を想定しています。本番実行前に検証してください。

よかったらシェアしてね!
  • URLをコピーしました!
  • URLをコピーしました!
目次