Range("A1")のA1って""で囲むの?


Excelを教えて25年以上が過ぎました。四半世紀です。私も歳を取るはずです。その間、数万人を超える「VBAって何ですか?まったく分かりません」というレベルの超初心者に教えてきましたが、正直言って「えぇ?そこ?」って感じる質問もたくさん受けました。まぁ、この「今さら聞けないVBA」では、そういう質問を多く取り上げているのですが。そんな「えぇ?そこ?」って感じる質問の中で、長い間「質問者が、本当は何で悩んでいるのか」という本質を、私が理解できなかったものがあります。それが、この質問です。たとえば、オブジェクト式を理解する上で、最も基本的な書き方である

Sheets("Sheet2").Name = "test"

というコードを示して「何か質問はありますか?」と聞くと、かなり多くの方から次のように聞かれます。

Sheet2ってダブルコーテーション("")で囲むんですか?

あるいは、セルに値を代入するという、これまたVBAでは基本中の基本である

Range("A1").Value = 100

を説明すると、こちらも同じような質問が多いです。

A1ってダブルコーテーション("")で囲むんですか?

私は最初、この質問を「文字列はダブルコーテーション("")で囲む」という、いわばプログラミング言語の大原則に関する内容だと思いました。だから、そのための解説をしました。たとえば、セル内に関数を入力するとき「=COUNTIF(A1:A5,"田中")」の田中は単なる文字ですよね。単なる文字はダブルコーテーション("")で囲みますよね。VBAも、それと同じなんですよ~みたいに。VBAは分からなくても、いつも使い慣れているワークシート関数で説明すれば理解してくれるだろうと。こうした回答を何度かしたのですが、どうも質問者は納得しないようでした。「・・・は、はぁ」みたいなw こちらも、今ひとつ手応えを感じていません。もちろん、コンピュータがメモリ内で行っている仕組み的な説明をしてもいいですが、おそらくそれだと、さらに混乱するでしょう。この手の質問、メチャクチャ多いんですけど、いったいどう説明すれば理解してくれるのだろうと、けっこう悩んでいました。それが、5~6年前になって、ようやく分かりました!この質問の真意を理解できました。Excelを教える者として、ほんの少しレベルアップできた感があり、その晩は祝杯をあげました。まぁ、それとは関係なく、いつも飲んでますけど。ちなみに「なぜ文字列はダブルコーテーション("")で囲まなければいけないのか」という、VBAの"仕組み"的な話は、下の動画で詳し~く解説しています。ああ、あと、ダブルコーテーション("")を「""」だったり「"""」だったり「""""」みたいに記述されているのを見たことはありませんか?その仕組みも解説していますので、ぜひご覧ください。

Excelを学習する順番

Excelは「機能」「関数」「VBA」の3要素で構成されています。「機能」というのは、ユーザーがマウスやキーボードでExcelに指示を与えて、Excelが何らかの動作をするという仕組みです。「関数」はSUM関数やVLOOKUP関数などのワークシート関数を駆使して、セル内で計算する仕組みです。そして「VBA」、これはマクロを使ってExcelを自動実行させる仕組みです。Excelは、この3要素で構成されているのですが、一般のユーザーは「機能」→「関数」→「VBA」の順番で学習することが多いです。つまり、これからVBAを学習しようという初学者は、すでに「関数」つまり、"セル内に入力する数式"の使い方に慣れているんです。Excelというアプリケーションに関しての学習で「機能」→「関数」まで来ました。となれば当然、これから学習する「VBA」も「機能や関数で学習してきた常識がVBAでも通用する。だって同じExcelなのだから」と考えて当然です。まずは、そこです。それは誤解です。「機能」「関数」と「VBA」は違います。つまり、「機能」「関数」で慣れ親しんできた"Excelの常識"と、"VBAの常識"は違います。違うんです。違うんだと思ってください。これを一緒だと感じている方がとても多いです。すると先のような疑問が生じます。

なぜ、「機能」「関数」という"Excelの常識"と、"VBAの常識"が異なるかというと、両者は別々に開発されたソフトウェアだからです。Excelは表計算ソフトです。データを並べ替えたり印刷したり、セル内に関数を入力して計算できます。Excelはそのように作られました。一方のVBAは、もともとあった「Visual Basic(通称VB)」というプログラミング言語を、Excelのセルやシートを操作できるように改良したものです。

ですから、「機能」や「関数」で当たり前だったことが、「VBA」では異なるということが起きます。両者の違いをいくつかご紹介しましょう。以下はどれも、VBAのセミナーで"超あるある"の質問ばかりです。

違い1:セルのアドレスやシート名は""で囲む

冒頭の質問です。なぜ多くのビギナーがこれを勘違いするのかというと、セルの中で使う数式はダブルコーテーション("")で囲まないからです。

Sheets("Sheet2").Range("A1").Value = 100

上記の「ダブルコーテーション("")で囲むんですか?」という質問は「(セルの中に入力する数式では囲まないのに、VBAでは)ダブルコーテーション("")で囲むんですか?」という意味だったんですね。お答えは「はい、そうです、囲みます」です。さらに「セルの中に入力する数式では囲まないのに、なぜVBAでは囲むんですか?」という疑問に対しては「ワークシート上のルールと、VBAのルールは違うから」が答えです。もし、これでも納得できないようでしたら、VBAは無理ですから諦めてください。

違い2:自動的に変わらない

この件に関する質問も超多いです。たとえばセルに次のような数式を入力したとします。

A列全体を選択して、列を挿入します。それまでセルA1だったセルは、1列右に移動してセルB1になります。

すると、セルに入力した参照式のアドレスも、自動的に変化します。

あるいは、別シート上のセルを参照していたとします。

ここで、参照先のシート名を手動操作で変更します。

すると、参照式で指定していたシート名も自動的に変化します。

ワークシート上では、行や列の挿入または削除によって、参照しているセルのアドレスが変化すると、そのセルを参照していた数式内のアドレスも自動的に変わります。別シートを参照しているときのシート名も同様です。このようにワークシート上では「ユーザーが手動操作でExcelに何かをすると、数式内に記述したことが自動的に変化」します。しかしVBAでは、Excel上で何かが起きたからといって、マクロのコードが自動的に変わるということは一切ありません。マクロのコードは、ただ記述されているだけで、Excelの"状況"とはリンクしていません。ですから、マクロを記述したあとで、たとえばセルの位置が移動してアドレスが変わったり、シートの名称が変わったときなどは、自分でマクロのコードを書き換えなければなりません。

Range("A1").Value = 100  ''アドレスは変化しない
Sheets("Sheet2").Select  ''シート名は変化しない

違い3:マクロを書いただけでは何も起きない

これも過去に何度か質問されました。今になって思えばこれも、VBAを"Excelの常識"で考えてしまったのが原因です。たとえば、セルに次のような数式を入力したとします。

セルC1に「=IF(A1="田中",B1*2,"")」という数式を入力して、セルC9までコピーしました。この結果、Excelは「A列が"田中"であるとき、C列に、B列の数値を2倍した値を表示する」という状態になります。これと、同じようなことをマクロでやる場合、たとえば標準モジュールに、次のようなコードを記述します。

Sub Macro1()
    Dim i As Long
    For i = 1 To 9
        If Cells(i, 1) = "田中" Then
            Cells(i, 3) = Cells(i, 2) * 2
        End If
    Next i
End Sub

このコードも「A列が"田中"であるとき、C列に、B列の数値を2倍した値を代入する」という、Excelに対する指示・命令です。結果だけを考えれば、先の数式と同じですが、両者はまったく異なります。数式は、セルにそれを記述するだけで、ただちに結果が現れます。しかしマクロは、このコードを"書いただけ"では何も起きませんし、セルには何も表示されません。「マクロって、実行しないといけないんですか?」という質問は、マクロとして記述したコードと、セル内に記述した数式の、どちらも同じ「Excelに対する指示・命令」だと考え(そこまでは合っています)、「機能」「関数」で培った"Excelの常識"と同じように「(マクロも)指示・命令は記述するだけで、ただちにExcelの状態が変わる」という誤解から生じたものでしょう。

また、似たような質問で、次のようなこともありました。マクロのコードを書いて、それを実行し、セルに値が代入されたあとで「手動でC列のセルをクリアしてください」と言ったところ「(モジュールにマクロを書いてあるのに)消えるんですか?」みたいな。これも、"Excelの常識"と混同した誤解です。

数式はセルの中に記述されている間はずっと、同じ計算結果を表示し続けます。マクロも同じ指示・命令ですが、セルとコードをリンクさせたわけではありません。人間が手動操作でセルに数値を代入するという行為を、マクロで代行しただけです。


最後の「違い3」みたいな質問は、それほど多くありませんが、それでも誤解する根本は同じです。対して「違い1」と「違い2」は、毎週のように実施しているVBAセミナーで、ほぼ毎回まったく同じ質問をされます。超定番の"あるある質問"です。正直に言いますが、マクロができるようになった人って、このへんは誰に教わるでもなく、自ら理解して進んできました。だから、そういう人が教える側になると、このへんの「自分にとっては当たり前」のことを軽視します。しかし、初学者というのは、こういうところで悩むんですよね。ビギナーからの「えぇ?そこ?」という質問をたくさん受けてきた私には、よく分かります。もし、この部分でモヤモヤしている人は、"Excelの常識"と"VBAの常識"は違うんだという認識からスタートしてください。