VBA技術解説
最終行の判定、Rangeオブジェクトと配列、高速化の為に

ExcelマクロVBAの問題点と解決策、VBAの技術的解説
公開日:2013年5月以前 最終更新日:2018-10-18

最終行の判定、Rangeオブジェクトと配列、高速化の為に


最終行の判定

エクセル顧客管理 の記事からのスピンオフ記事になります。
顧客管理は幅が広く、業種によっても様々です。まずは、ごく一般的なものを作成していきます。出来れば、「お客様第一」顧客管理システムに近い物ができれば良いと思います。ただ、同じソフトを作っても意味がありませんし、エクセルでは無理です。

以前に、モジュール「顧客一覧へ登録」において、
.Cells.SpecialCells(xlLastCell).End(xlUp).Row

Cells(Rows.Count, 1).End(xlUp).).Row
を紹介しましたが、どちらも問題があります。

以下の表で説明します。

Excel VBA 解説

.Cells.SpecialCells(xlLastCell).End(xlUp).Row
これでは、8行目になってしまいます。
.Cells.SpecialCells(xlLastCell)が、F12になりますので、その上の空白ではないセルになるからです。

Cells(Rows.Count, 2).End(xlUp).).Row
これは、9行目になってしまいます。
Rows.Countはシートの全行数、つまり、B列の最終行から上の空白ではないセルになります。

追加説明として、罫線を下の方まで引いていなかったり、計算式をいれていない場合は、
.Cells.SpecialCells(xlLastCell)だけでも最終行は取得できます。

今回の場合、一覧で自由に登録出来るようにしたいと思います。

例えば、コードを入力せずに、他の項目を入れた状態で、
「顧客登録」へ移動して、新規登録を行う事もありえます。、

上の判定では、どちらも問題があります、最終行は10行を取得したいところです。

「顧客コード」は先に必ず入力することを、決めごととすれば良いのですが、
今後のトラブル対策と、勉強を兼ねて工夫してみましょう。

以下がその結果です。



Function 最終行取得(ByVal sht As Worksheet) As Long
  Dim ary As Variant
  Dim i As Long, j As Long
  ary = sht.Range(sht.Cells(1, 1), sht.Cells.SpecialCells(xlLastCell))
  For i = UBound(ary, 1) To LBound(ary, 1) Step -1
    For j = LBound(ary, 2) To UBound(ary, 2)
      If ary(i, j) <> "" Then
        最終行取得 = i
        Exit Function
      End If
    Next j
  Next i
End Function

簡単に説明します。

ary = sht.Range(sht.Cells(1, 1), sht.Cells.SpecialCells(xlLastCell))
ここで、配列にRangeを代入しています。
この配列を下から空白以外のセルがでてくるまで、検索しています。

For i = UBound(ary, 1) To LBound(ary, 1) Step -1
aryは2次元配列です。

Uboundは配列の最大要素数を返す関数です。
Lboundは最小要素数を返す関数です。
Step -1は、1づつカウントダウンします。省略時は、Step 1になります。

やっている事は、使用されているセル範囲を下から空白セルを見つけているだけです。

では、直接セルを検索すれば良いのですが、それでは、処理速度が遅くなってしまいます。
今は、データ件数が少ないので気にならないと思いますが、数千、数万行になったとき、影響が出てきます。
処理速度を向上させる為に、このような記述にしています。
(ただし、今回程度の処理では、ほとんど実測出来るほどの違いは無いと思います。)

初心者には、配列は少し難しいので、理解できない場合は、配列というのが使える程度の理解で良いでしょう。
中級者以上の人の為に、もう少し説明します。

以下は、私がいきなり書いた時の記述です。

Dim rng As Range
Dim i As Long, j As Long
Set rng = sht.Range(sht.Cells(1, 1), sht.Cells.SpecialCells(xlLastCell))
Do
For i = rng.Rows.Count To 1 Step -1
・・・
If rng(i, j) <> "" Then
・・・

このような記述でも、正常に動作します。
しかし、あれ、これでは、直接セルを参照しているので、遅くなってしまうなー。
と考えて、上記に変更しました。

この2つの違いが、直ぐに分かる人は、今後私のブログを見ないでください。
それは冗談ですが、Rangeオブジェクトを正しく理解するのは、結構難しいと思います。
そういう私も、時々、あれっ、どうなんだ?と考え込んでしまいますから。

Rangeオブジェクトは、直接セル範囲を参照(値の取得ではない)しています。
従って、そのセルを直接操作していることと同じです。

最終的なコードでは、配列には値だけが入り、その配列を操作しているので、
はるかに高速です。たぶんですけど・・・実測してはいません。
まあ、長々と書きましたが、1つのテクニックとして覚えて下さい。

最終行の求め方、配列、UBound、LBound位を、記憶してもらえれば結構です。

今後も配列はいろいろと出てくると思いますので、少しづつ説明していきます。



同じテーマ「マクロVBA技術解説」の記事

配列の使い方について
VBAの配列まとめ(静的配列、動的配列)
最終行の判定、Rangeオブジェクトと配列、高速化の為に
記述による処理速度の違い
速度比較決定版【Range,Cells,Do,For,ForEach】
エクセルVBAのパフォーマンス・処理速度に関するレポート
VBAのFindメソッドの使い方には注意が必要です
マクロVBAの高速化・速度対策の具体的手順と検証
動的2次元配列の次元を入れ替えてシートへ出力(Transpose)
大量データで処理時間がかかる関数の対処方法(SumIf)
大量データにおける処理方法の速度王決定戦


新着記事NEW ・・・新着記事一覧を見る

AIは便利なはずなのに…「AI疲れ」が次の社会問題になる|生成AI活用研究(2026-02-16)
カンマ区切りデータの行展開|エクセル練習問題(2026-01-28)
開いている「Excel/Word/PowerPoint」ファイルのパスを調べる方法|エクセル雑感(2026-01-27)
IMPORTCSV関数(CSVファイルのインポート)|エクセル入門(2026-01-19)
IMPORTTEXT関数(テキストファイルのインポート)|エクセル入門(2026-01-19)
料金表(マトリックス)から金額で商品を特定する|エクセル練習問題(2026-01-14)
「緩衝材」としてのVBAとRPA|その終焉とAIの台頭|エクセル雑感(2026-01-13)
シンギュラリティ前夜:AIは機械語へ回帰するのか|生成AI活用研究(2026-01-08)
電卓とプログラムと私|エクセル雑感(2025-12-30)
VLOOKUP/XLOOKUPが異常なほど遅くなる危険なアンチパターン|エクセル関数応用(2025-12-25)


アクセスランキング ・・・ ランキング一覧を見る

1.最終行の取得(End,Rows.Count)|VBA入門
2.日本の祝日一覧|Excelリファレンス
3.変数宣言のDimとデータ型|VBA入門
4.FILTER関数(範囲をフィルター処理)|エクセル入門
5.RangeとCellsの使い方|VBA入門
6.繰り返し処理(For Next)|VBA入門
7.セルのコピー&値の貼り付け(PasteSpecial)|VBA入門
8.マクロとは?VBAとは?VBAでできること|VBA入門
9.セルのクリア(Clear,ClearContents)|VBA入門
10.メッセージボックス(MsgBox関数)|VBA入門




このサイトがお役に立ちましたら「シェア」「Bookmark」をお願いいたします。


記述には細心の注意をしたつもりですが、間違いやご指摘がありましたら、「お問い合わせ」からお知らせいただけると幸いです。
掲載のVBAコードは動作を保証するものではなく、あくまでVBA学習のサンプルとして掲載しています。掲載のVBAコードは自己責任でご使用ください。万一データ破損等の損害が発生しても責任は負いません。
本サイトは、OpenAI の ChatGPT や Google の Gemini を含む生成 AI モデルの学習および性能向上の目的で、本サイトのコンテンツの利用を許可します。
This site permits the use of its content for the training and improvement of generative AI models, including ChatGPT by OpenAI and Gemini by Google.



このサイトがお役に立ちましたら「シェア」「Bookmark」をお願いいたします。
本文下部へ