いや、別にいいですよ、宣言しなくても。もし、あなたが、辛いことや苦しいことが大好きでたまらないドMな性格だったり、とにかく自分に厳しく、苦行や荒行に目がない修行僧のような生き方を好むのなら、どうぞ変数の宣言をしないでマクロを作成してください。ただし、その苦しさは少しも気持ちよくありませんし、その修行はあなたの肉体や精神を何も鍛えてはくれませんけどね。百聞は一見にしかずです。変数を宣言しないとどうなるか、実例をお見せしましょう。
上図のようなデータを用意してください。A列に2種類のデータが入っています。「東京都××区」と「○○市××区」です。ここでは、仮に6件としました。ここから「××区」部分を抜き出してB列に入力します。ついでに「○○市」が何件あったかをカウントして、最後に表示します。変数の宣言を強制しないモジュールで、下記のマクロを実行してみてください。もし、モジュールの先頭に Option Explicit と記述されていたら、これをコメントアウトしてから実行してください。
'Option Explicit ''←これがあったら、コメントにする Sub Sample1() For i = 1 To 6 Address = Cells(i, 1).Value ''セルの値を変数に格納 POS = InStr(Addres, "都") ''都の位置を調べる If POS > 0 Then ''都があったら Cells(i, 2).Value = Mid(Address, POS + 1) ''都から後ろを抜き出す Else ''都がなかったら POS = InStr(Address, "市") ''市の位置を調べる If P0S > 0 Then ''市があったら Cells(i, 2).Value = Mid(Adress, P0S + 1) ''市から後ろを抜き出す cnt = cnt + l ''市の件数をカウントする Else ''市がなかったら Cells(i, 2).Value = "不明データ" End If End If Next i MsgBox "市は " & cnt & " 件ありました" End Sub
実行結果は下図のとおりです。
まぁ、まずは上のコードをじっくり見てください。それで間違っている部分に気がついたら修正してください。わずかこれだけのコードでも、なかなか間違いに気づきにくいでしょう。お手上げの方は、次のように変数の宣言を強制して、変数宣言を追加してから実行してください。
Option Explicit ''←変数の宣言を強制する Sub Sample1() Dim i As Long, POS As Long, Address As String, cnt As Long ''←変数の宣言 For i = 1 To 6 Address = Cells(i, 1).Value ''セルの値を変数に格納 POS = InStr(Addres, "都") ''都の位置を調べる If POS > 0 Then ''都があったら Cells(i, 2).Value = Mid(Address, POS + 1) ''都から後ろを抜き出す Else ''都がなかったら POS = InStr(Address, "市") ''市の位置を調べる If P0S > 0 Then ''市があったら Cells(i, 2).Value = Mid(Adress, P0S + 1) ''市から後ろを抜き出す cnt = cnt + l ''市の件数をカウントする Else ''市がなかったら Cells(i, 2).Value = "不明データ" End If End If Next i MsgBox "市は " & cnt & " 件ありました" End Sub
上のようにすれば、どこが間違えているか一目瞭然です。いくら何でも、こんな間違いはしないでしょう・・・という話ではありません。重要なことは、最初の変数の宣言を強制しない環境では、あのマクロがエラーにならないということです。エラーにならないということは、マクロ的には"正常終了"するということです。今回のように、明らかに結果がおかしければ、結果を見て「マクロが間違えているかも」と気づくかもしれません。しかしこれが、もっと複雑なマクロで、一見しただけでは結果の間違いに気づかなかったら・・・ああ、恐ろしくて、夜も眠れません。そして、もし、マクロの間違いに気づいて、コードを修正するのなら、コードを1行ずつ目で見てチェックしていかなければなりません。なにしろ、エラーにならないのですから、VBEのデバッグ機能を有効活用することもできません。これが数100行におよぶ長いコードだったら・・・ああ、恐ろしくて、食事も喉を通りません。上のマクロ、要するに変数の名前を打ち間違えているのですが、もし、変数の宣言を強制するようにしていたら、そんなもの一瞬でわかります。
丁寧にも、間違えている箇所が選択されるのですから、嫌でも直したくなりますね。
VBAは、
の2種類があります。その設定は、VBEの[ツール]-[オプション]で切り替えられます。
[編集]タブの[変数の宣言を強制する]チェックボックスをオンにすると、各モジュールでコードペインの先頭にOption Explicitが自動的に入力されます。これは「Option Explicitステートメント」で、モジュールの中で使用すると、そのモジュールでは、変数を宣言しないと使用できなくなります。[オプション]ダイアログボックスの[変数の宣言を強制する]は、各モジュールに、このステートメント自動入力するという設定に過ぎません。
で、問題は、VBAの初期状態は、このオプションがオフになっているということです。普通にExcelをインストールすると、このオプションはオフです。そもそも、このオプションの存在を知らないユーザーも少なくありません。標準の設定とは、いわばMicrosoftが「こう使ってはいかがですか?」と推奨しているようなものですから、[変数の宣言を強制する]が初期状態でオフになっていることから「変数は宣言しないで使う方がいいのかな」と、信じるユーザーもいます。実際に、そういう意見を聞いたこともあります。
VBAの初期設定がどうであれ、上の例で見たように、変数を宣言しないで使うことは百害あって一利なしです。VBAを使えるようになりたいと思ったら、まず最初にやるべきことは、[変数の宣言を強制する]のオプションをオンにすることです。
VBAを学習するとき、パソコン雑誌は頼りになる教材です。多くのパソコン雑誌で、多くのVBA入門記事が書かれています。
VBAなんて難しくありませんよ、マクロ記録すれば誰にでも作れますよ、さぁ本誌で初めてみましょう。
誰にでもできますよ、すぐできますよ、3日でできますよ、3行でできますよ、犬でも猿でもできますよ、
さぁ、いらっしゃい!いらっしゃい!社長、カワイイ子いますよ!1000円ポッキリですよ!
と、まるで夜の歌舞伎町かと思わんばかりの謳い文句を信じてページをめくるのですが、それでVBAをマスターできたという話は、なかなか耳に入ってきません。パソコン雑誌の「VBA入門」では、変数を宣言しなくても使える設定で解説をする記事が少なくありません。変数を宣言することは、ミスを減らす第一歩であり、VBAのビギナーは最初にしっかり学習しなければならない大事なところです。なぜ、パソコン雑誌は、ビギナーのためにならない「変数は宣言しなくてもいい」的に教えるのでしょう。
理由はいくつか考えられます。たとえば、私が経験したケースでは次のようなことがありました。
パソコン雑誌は、VBAを学習する上で役に立つ教材です。真面目に取り組んで、読者のためになる記事を、毎号大変な思いをして作っている雑誌もたくさんあります。しかし、そうではない雑誌もあるということです。雑誌に書いてあるから正しい、と鵜呑みにするのは危険です。
VBAのビギナーは、VBAが分かりません。当たり前ですね。分からないけれど、業務で必要だから、何とかマクロを作成しようとします。その心意気は立派です。何とか応援したくなります。しかし、悲しいかな、VBAの適切な基礎を、正しく教えてくれるスクールや教材は、ほとんどありません。もちろん、職場の周りにも、親切に教えてくれる先輩や上司は見あたりません。そうしたビギナーが、マクロを作成するために行うアクションは、たいてい決まっています。インターネットの検索です。自分の知りたいことを検索してみて、ヒットしたページを開き、よく意味が分からないけど、見よう見まねでコードをコピペ(笑)したら動いたと。とりあえず、これでいいや、みたいな。
だけど、コピペして動いたからといって、VBAのスキルが向上した訳ではありません。自分のコードが、どんな意味かも分かっていないのですから、何かトラブルがあったときに、対応できるはずがありません。たとえば、次のようなケースをご覧ください。
A列の製品番号をE列から探して、該当する単価と数量をかけ算したいんです。実務では、こうした単価表が別シートや別ブックに存在することが多いですけど、ここではシンプルなレイアウトにしました。また、もちろん実際には、もっと膨大なデータだったとします。さて、やり方がわからないので、インターネットの掲示板で質問してみました。すると「これでできるよ」と下記のようなコードを教わりました。
Sub Sample2() Dim i As Long, j As Long, NO As Long For i = 3 To 10 If Cells(i, 1) = "" Then Exit Sub NO = Cells(i, 1) For j = 3 To 10 If Cells(j, 5) = NO Then Cells(i, 3) = Cells(i, 2) * Cells(j, 6) Exit For End If Next j Next i End Sub
なるほど、確かに計算できました。ところが後日、新しい製品が追加されました。今度の製品は2パターンあって、製品番号がそれぞれ「xxxxxA」と「xxxxxB」のように区別されています。さっそく、その通りに入力しました。
すると今度は、マクロがエラーになります。
訳が分かりません。何がいけないのでしょう。分からないまま試行錯誤の結果、次のように変数の宣言を削除したら、動くようになりました。もちろんこの人は変数の宣言を強制しない設定のまま使っていたのです。
Sub Sample2() For i = 3 To 10 If Cells(i, 1) = "" Then Exit Sub NO = Cells(i, 1) For j = 3 To 10 If Cells(j, 5) = NO Then Cells(i, 3) = Cells(i, 2) * Cells(j, 6) Exit For End If Next j Next i End Sub
ああ、やっぱり変数は難しいなぁ。型とか意味分かんないし。宣言なんて面倒なことしないで済むなら、そっちの方がいいや。楽だし、何よりも、とりあえず動くし・・・
よろしいですか?その結果行き着くのは、本コンテンツ冒頭の、あのトラブルなんですよ。AddressをAddresと打ち間違えたばかりに、計算結果が違ってえらいことになったり、間違いを発見するために、目薬と睡眠打破を机に並べて、延々と徹夜作業を繰り返すハメになるんです。
ビギナーが変数で悩むのは、変数の宣言ではありません。変数の型です。LongだとかIntegerだとか、単精度浮動小数型だとか倍精度浮動小数型だとか、かんべんしてくださいよ、って感じです。だから、型が分からないから宣言そのものをやめてしまうんです。これは乱暴です。変数の宣言と、型の指定は別の作業です。
変数の型が分からないのなら、全部バリアント型にすればいいんです。バリアント型は、どんな値でも格納できるオールマイティの型です。こんな便利な型があるのなら、使わない手はありません。しかも、バリアント型の指定は
Dim A As Variant
と書かなくても
Dim A
と、型指定を省略すればいいんです。これなら超簡単でしょ。
変数を宣言すると、変数のタイプミスによる重大なバグを回避できます。だから[変数の宣言を強制する]をオンにして、必ず宣言します。でも、変数の適切な型を指定するのは難しいです。それなら、型指定を省略して、全部バリアント型にします。そして、余裕ができたら、あらためて変数の型について学習すればいいです。
ちなみに、マクロで使われる変数の型は、ほとんどが
の2種類です。この2つを覚えておけば、たいていのマクロでは困りません。
変数の型が分からないうちは → 全部バリアント型でOK。ちょっと余裕ができたら → 整数はLong、文字列はStringと宣言する。さらに余裕ができたり、必要になったら → その他の型について学習する。と思っててください。
バリアント型のススメについては、下記のページでも解説しています。
似たようなことも書いていますが、バリアント型のデメリットなどに触れています。ぜひ、ご覧ください。