ExcelマクロVBA技術解説 | VBAの省略可能な記述について | ExcelマクロVBAの問題点と解決策、エクセルVBAの技術的解説



最終更新日:2018-08-11

VBAの省略可能な記述について


VBAには、省略可能な記述が数多くあります、

省略可能な記述とは、書いても書かなくても動作に何の違いもないものになります。

VBAのこの記述の自由度は、慣れてしまえば楽なものですが、

初心者の方が覚え始める時には、多少混乱することもあると思います。



基本的な考え方としては、
・省略できるものはなるべく省略して書く
・省略しない方が読みやすい場合は省略しない
書くか書かない迷ったときは、このような判断をしてください。

マクロはVBAで書く手順書になります。
明瞭かつ簡潔で、わかり易く読みやすい方が良いに決まっています。

ただし、省略する場合は省略形を書いているという事を承知した上で書く方がより良いです。
省略していると承知した上で、省略しても何も問題が無い場合は省略するという考えになります。

以下では、VBAの省略可能な代表的な記述について取り上げます。
下記以外にもまだ有りますが、このくらいについて理解していれば十分でしょう。


変数の宣言

VBE→ツール→オプション→変数の宣言を強制する



ここにチェックを入れている場合は、新規モジュール作成時にはモジュールの先頭に、
Option Explicit
この一文が自動挿入されます。

このOption Explicitがある状態であれば、変数は必ず宣言しなければなりません。
変数宣言をしない場合はエラーになります。
しかし、
Option Explicitが無ければ、変数は宣言しなくても問題なく動作します。

Option Explicitが無い状態での変数宣言は、
データ型指定においては意味をもちますが、勧められる使い方ではありません。
といいますか、
必ずOption Explicitを指定して、変数は必ず宣言するようにして下さい。


変数宣言のデータ型

Dim i
Dim i As Long
これらは、どちらでも動作にほとんど違いはありません。
「ほとんど」と書きましたが、100%同じ動作というわけではありません。
例としては、
Ifステートメントで比較する場合に違いが発生する場合があります。
Sub test1()
  Dim i
  Dim j
  i = 123
  j = "123"
  If i = j Then
    MsgBox "同じ"
  Else
    MsgBox "違う"
  End If
End Sub

この結果は、「違う」となります。
しかし、
変数iまたは変数jのどちらかでも、
Dim i As Long
このように宣言すると、「同じ」となります。

※このような動作になる理由は、Variantの説明をかなり詳細に説明しなければなりませんので、ここでは省略します。
変数の型を省略すると、Variantになります。
Dim i
これは、
Dim i As Variant
このように宣言したことと同じになります。

指定すべきデータ型が不明な場合は、省略またはVariant指定でも構いませんが、
可能な限り、分かる範囲内でデータ型を指定するようにしましょう。

固有オブジェクト型について
固有オブジェクト型とは、例えば、
Dim sht As Worksheet
このようにオブジェクトの型を指定するものの事です。
WorksheetやWorkbook程度は直ぐに分かりますが、
オブジェクトの中にはオブジェクトの型が直ぐには分からない場合もあります。
特に、オブジェクトのプロパティで参照されるオブジェクト(子供のようなオブジェクト)の場合、
必ずしもプロパティ名と一致していない場合もあるため、正しいオブジェクトの型が分からない場合が出てきます。
オブジェクトの型が不明な場合は型を省略してVariantで構いません。
【参考】


Application.ScreenUpdating = True
Application.DisplayAlerts = True

マクロ開始の先頭の方で、
Application.ScreenUpdating = False
Application.DisplayAlerts = False
これらで、画面描画とアラートを止める指定をしている場合が多いです。
そこで、これらをTrueに戻さなくて良いのか、戻し忘れたらどうなるか・・・
結論としては、マクロの一連の動作が終了した時点で、自動的にTrueに戻ります。
従って、Trueに戻さなくても問題はありません。
※エラーでマクロが停止した場合はScreenUpdatingが戻らない場合があります。

では、Trueに戻す記述をし鵜略して良いかどうかという事ですが、
なるべくTrueに戻した方が良いでしょう。
ScreenUpdating、DisplayAlerts以外にも、Applicationのプロパティでマクロ開始時点で変更している場合も多々あります。
Applicationのプロパティの中には、マクロ終了時点で元に戻らないものが多数あります。
Application.EnableEvents = False
Application.Calculation = xlCalculationManual
これらは、マクロが終了してももとには戻りません。

すると、マクロ開始時点で、
Application.ScreenUpdating = False
Application.DisplayAlerts = False
Application.EnableEvents = False
Application.Calculation = xlCalculationManual
このように記述しているとしたら、マクロ終了時の記述として、
Application.ScreenUpdating = True
Application.DisplayAlerts = True
Application.EnableEvents = True
Application.Calculation = xxlCalculationAutomatic
このように記述することが自然であり、
あえてScreenUpdatingとDisplayAlertsだけを記述しない理由は見当たりません。

結論としては、
ScreenUpdatingとDisplayAlertsだけしか使っていないとしても、
マクロ終了時の記述としてもとに戻すくせを付けておいた方がより良いと思います。
ただし、これは必須と言うほどのものではなく、書いておくに越したことはないという程度のものです。

【参考】


Applicationのプロパティ

ActiveCell
ActiveSheet
ThisWorkbook
これらは詳しくは、Applicationのプロパティになります。
つまり、
Application.ActiveCell
Application.ActiveSheet
Application.ThisWorkbook
これらのApplicationが省略された状態です。
さすがに、これらにApplicationを付けて書いているのはほとんど見かけません。
これらのApplicationは省略して書くべきでしょう。

WorksheetFunctionもApplicationのプロパティです。
※WorksheetFunction自体はClassですが、
  ApplicationのWorksheetFunctionプロパティを経由して参照します。
このApplicationは省略できます。
書いても構いませんが、記述が長くなるので省略した方が見やすいと思います。

Applicationのプロパティでも、ScreenUpdatingやDisplayAlertsはApplicationを省略できません。
いきなり、ScreenUpdatingと書いてしまうとエラーとなります。

【参考】

Applicationを省略できるプロパティと、省略できないプロパティについて
オブジェクトブラウザー(VBEでF2で起動)



このグローバルに入っているものは、Applicationを省略できます。
Applicationのプロパティで、ここに無いものはApplicationを省略できません。


Applicationのメソッド

省略できるかどうかは、Applicationのプロパティと同様になります。
グローバルに入っているものは、Applicationを省略できます。
SendKeys
Intersect
Union
これらは、グローバルに入っているので省略可能です。
ただしプロパティと違って、省略できるメソッドは極めて稀です。

上記以外には、直ぐに思いつくものがありません。
上記の3つのメソッドについては良く使われるものですので、
Applicationを省略できることも結構知られているので省略して構わないでしょう。
少なくとも私は省略して書いています。

ただし、記述を見ただけでは関数との区別がつかないので、あえてApplicationを書くという考え方もあります。
初心者の方とVBAを共有する場合は、Applicationを書いておいた方が無難かもしれません。

【参考】


Range.Value

このValueについては、
多くの場合は省略できるのですが、一部省略できない場合が存在します。
セルに値を入れるだけの記述なら、
Range("A1").Value = "abc"
Range("A1") = "abc"
これらに動作の違いはありませんので、
多くのセルに値を入れる場合は読みやすさを考えれば省略した方が良いでしょう。
実際に私も、値を入れる場合はほぼ省略しています。

ただし、Valueプロパティとして考えたときには、前述のとおり省略できない場合もあるので気を付けて下さい。
以下の参考ページを是非お読みください。

【参考】


プロシージャーのCall

SubプロシージャーやFunctionプロシージャーを呼ぶ時に、
Call Subプロシージャー名
Call Functionプロシージャー名
これらは、Callを省略して、
Subプロシージャー名
Functionプロシージャー名
このように記述しても、動作に何らの違いもありません。

ですが、これらのCallはなるべく書いた方が好ましいと考えます。
VBAを書いている人は、SubプロシージャーやFunctionプロシージャーの存在が分かっているので、
Callを書いても書かなくても、読んでいて違和感を感じないのですが、
他人がCallが省略されたVBAを読むと、一瞬「これは何?」というような感覚になる場合があります。
特に英語のプロシージャー名だと、ぱっと見た目では何者なのかが分かりずらい場合があるという事です。

【参考】


メソッドのCall

ここのでメソッドとは、VBAに用意された(Range等の)メソッドの事になります。

メソッドの戻り値を使用しない場合は、いきなりメソッドから書き始める場合が多くあります。
例えば、
Range.AutoFilter Field:=1, Criteria1:="a"
これは、Callを付けて書くことが出来ます。
Call Range.AutoFilter(Field:=1, Criteria1:="a")

世の中のVBAコードのほとんどは、この場合のCallはし省略されて書かれています。
慣例には従った方が無難なので、このCallは省略して書いた方が良いでしょう。

ただし、メソッドの戻り値を使う場合は、括弧()が必要になるので、混乱しないようにして下さい。

【参考】


Let

変数への代入の際には、
オブジェクト変数なら、
Set 変数 = オブジェクト
と書きますが、通常データの変数の場合は、
変数 = 値
と記述します。

変数 = 値
これを省略せずに全て書くなら、
Let 変数 = 値
と書くことになります。

しかし、このLetが書かれているVBAコードは見たことがありません。
さすがにこれは書くべきではないでしょう。

ヘルプにも、
「Letを明示的に使用するかどうかは表記上の問題であり、通常は省略します。」
このように書かれています。


Next 変数

For i = 1 To 10
  ・・・
Next i
この
Next i のiは省略できます。
つまり、
For i = 1 To 10
  ・・・
Next
これでよいという事です。
この場合、Nextの後ろに書くとしたらi以外は書くことが出来ません。
つまり、iと書くか、iを省略するかという選択になります。

VB(Visual Basic)の後継にあたる、Visual Studio の Visual Basicでは、
For i = 1 To 10ここまで書いてEnterすると、Nextが自動挿入されます。
Next iではなくNextが自動挿入されます。
つまりこれは、Microsoftがこのiは不要だといっていると判断して構わないはずです。

Forをネストした時に、どのForに対するNextかが分かるように、Nextの後ろに変数名を書いた方が良いという意見もあるようですが、
ネストの読みやすさを議論するなら、ただしくインデントすべきであって、これ以上の読みやすさ対策はありえません。

むしろコピペでVBAコードを使い回す時に、このiを書き換える手間が発生する事を考えれば、
むしろ省略した方が良いと考えます。

【参考】


Step 1

For i = 1 To 10
For i = 1 To 10 Step 1
これらは全く同一のものになります。
ForのStepをし省略した場合は、Step 1となります。

Step 1を書くことに何の不都合もありませんが、
このStep 1をわざわざ書く人は稀でしょう。

【参考】


引数が無い場合の()

変数 = Now
変数 = Now()
どちらでも構いません。
この括弧を書くかどうかは、個人の好みでしょう。

変数 = Dir(パス)
Do While 変数 <> ""
  ・・・
  変数 = Dir()
Loop
この、
変数 = Dir()
これは、
変数 = Dir
このように()を省略することが出来ます。
しかし、Dirの引数を省略した場合は次のファイル名を取得するという仕様を考えたとき、
引数が省略されていることを見た目でわかり易いように伝えるとすれば、括弧を書いた方が良いでしょう。

【参考】


名前付き引数

Range("A1:C10").AutoFilter Field:=1, Criteria1:="a"
この、Field:=やCriteria1:=を名前付き引数と呼びます。
これらの名前付き引数を省略して、
Range("A1:C10").AutoFilter 1, "a"
このように書いても、動作に何の支障もありません。



しかし、名前付き引数を省略する場合は、引数の指定順を厳密に守らなければなりません。
また、後でVBAコードを読んだときに、引数の意味が分からなくなってしまう事にもなりかねません。

一般的な習慣として、
VBA関数の引数には、名前付き引数を省略して書く
メソッドの引数には、名前付き引数を指定して書く
このような使われ方をしている場合が多いので、それに従っておいた方が無難でしょう。

VBA関数は引数が少なく、引数を覚えている人が多いが、
メソッドの引数は数が多い場合があり、引数を覚えていない人の方が多いという事が最大の理由でしょう。

【参考】


メソッドの規定値

Range("A1:C10").Sort Key1:=Range("A1"), Order1:=xlAscending
これは、
Range("A1:C10").Sort Key1:=Range("A1")
このように、ソート順を指定しなくても動作に問題はありません。
Order1の規定値が、xlAscendingなので省略しても良いという事になります。



しかし、
このOrder1の規定値がxlAscendingだと知っている人ばかりではないという事を考えれば、
ここは引数を省略せずに、Order1:=xlAscendingと書いておいた方が良いでしょう。

【参考】


組み込み列挙

Range("A1").Borders.LineStyle = xlContinuous
この、xlContinuousの列挙を省略せずに書くと、
Range("A1").Borders.LineStyle = XlLineStyle.xlContinuous
このようになります。

VBAで、Xl○○と言うものは列挙になります。
列挙の記述では、省略しない場合は、
列挙.メンバー
と記述することになります。



先の、Applicationのプロパティで書いた、グローバルに入っているため、
列挙のメンバーをいきなり書くことが出来ます。
一般的には、列挙のメンバーをいきなり書いている方が多いでしょう。
列挙のメンバーを調べる手段として、自動記録かネット検索になると思いますが、
どちらも、列挙のメンバーをいきなり書いている場合がほとんどになるからです。
つまり、省略した書き方しか知らない人が多数だという事です。

ただし、
XlLineStyle.xlContinuous
このように書いておくと、後々線種を変更したい時には楽になります。

【参考】


関数のモジュール名

VBA関数は、VBAが用意したモジュールに入っているものになります。
文字列系関数(Mid,Right等々)は、
Stringsと言うモジュールに含まれています。
つまり、
Strings.Mid
省略しなければ、このように書くという事になります。


日付時刻系(Date,DateSerial等々)は、
DateTimeモジュールに含まれています。


VBA関数は、グローバルに入っているので、いきなり関数から書き始められます。
関数のモジュール名については、むしろ知っている人の方が少ないので、
モジュール名が書かれているVBAコードにお目にかかることはほとんどないと思います。



コレクションのItem

Worksheets(1)
Worksheets.Item(1)
後者の書き方を見かけることは滅多にありませんが、
この二つは、全く同じものになります。
Workbooks等、他のコレクションでも同じ書き方が存在します。

Worksheetsはコレクションです。
VBAで扱うコレクションの多くでは、既定のプロパティとしてItemプロパティを持っています。
既定のプロパティとは、プロパティを省略した場合に適用されるプロパティという事になります。
従って、Itemを省略してもItemが指定されているものとされるという事になります。

Itemプロパティが既定のプロパティとなっているコレクションの場合は、Itemは省略して書かれることがほとんどです。

Rangeオブジェクトもコレクションです
Rangeオブジェクトもコレクションですが、他のコレクションとは少々異質のものになりますので注意してください。

MsgBox Range("A1:C10").Item(5).Address
MsgBox Range("A1:C10")(5).Address
この二つは同じ動作となり、結果は「$B$2」となります。

MsgBox ActiveSheet.UsedRange.Item(5).Address
MsgBox ActiveSheet.UsedRange(5).Address
前者は正しく動作しますが、後者は「不正なプロパティ」となります。
しかし、
Dim rng As Range
Set rng = ActiveSheet.UsedRange
MsgBox rng.Item(5).Address
MsgBox rng(5).Address
これなら、どちらも正しく動作します。

このようにRangeオブジェクトがコレクションだからと言って、
無条件かつ単純にItemを省略できるわけではありませんので、
Rangeオブジェクトの場合はItemを省略しない方が良いでしょう。


ステートメントと変数以外は、Applicationまたはモジュールに含まれているものになります。
従って、省略せずに全てを書くとすれば、
ステートメントと変数以外はApplicationまたはモジュール名から書き始めることになります。
しかし、これでは記述が長くなってしまい読みづらいコードになってしまいます。

まずは、あなたが読みやすいと感じる書き方から初めて、
ゆくゆくは、他人にも読みやすいVBAコードを書くようにすると良いでしょう。




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

If条件式のいろいろな書き方:TrueとFalseの判定とは
VBAにおける括弧()の使い方
VBAにおけるピリオドとカンマとスペースの使い方
変数とプロシージャーの命名について
文字列置換の基本と応用(Replace)
データクレンジングと名寄せ
ForとIfのネストこそがVBAの要点
For Next の使い方いろいろ
複数条件判定を行う時のコツ
VBAの省略可能な記述について

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

VBAの省略可能な記述について|ExcelマクロVBA技術解説(8月11日)
複数条件判定を行う時のコツ|ExcelマクロVBA技術解説(7月11日)
For Next の使い方いろいろ|VBA技術解説(6月14日)
VBAを定型文で覚えよう|ExcelマクロVBA技術解説(3月26日)
VBAスタンダード試験対策まとめ|MOS VBAエキスパート対策(3月16日)
ユーザーフォームとメニューの操作|MOS VBAエキスパート対策(3月14日)
ファイルの操作|MOS VBAエキスパート対策(3月14日)
ユーザーフォームの各種イベント|Excelユーザーフォーム(3月13日)
レジストリの操作|MOS VBAエキスパート対策(3月12日)
変数と配列|MOS VBAエキスパート対策(3月12日)

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

1.最終行の取得(End,Rows.Count)|VBA入門
2.変数とデータ型(Dim)|ExcelマクロVBA入門
3.セルのコピー&値の貼り付け(PasteSpecial)|VBA入門
4.Range以外の指定方法(Cells,Rows,Columns)|VBA入門
5.マクロって何?VBAって何?|ExcelマクロVBA入門
6.RangeとCellsの使い方|ExcelマクロVBA入門
7.とにかく書いて見よう(Sub,End Sub)|VBA入門
8.繰り返し処理(For Next)|ExcelマクロVBA入門
9.定数と型宣言文字(Const)|ExcelマクロVBA入門
10.マクロはどこに書くの(VBEの起動)|VBA入門



  • >
  • >
  • >
  • VBAの省略可能な記述について

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


    記述には細心の注意をしたつもりですが、
    間違いやご指摘がありましたら、「お問い合わせ」からお知らせいただけると幸いです。
    なお、掲載のVBAコードは自己責任で使ってください。万一データ破損等の損害が発生しても責任は負いません。





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

    本文下部へ

    ↑ PAGE TOP