Excel VBAのPublic変数についてお探しですね。

広告

Excel VBAのPublic変数(グローバル変数)の使い方と注意点を分かりやすく解説

Excel VBAで複数のモジュールに処理を分けていると、「あるモジュールで作った値を、別のモジュールでも使いたい」という場面が必ず出てきます。

そんなときに便利なのがPublic変数、いわゆるグローバル変数です。

Public変数はとても便利なのですが、どこからでも参照・変更できるため、使い方を間違えると「あれ、なんでこの値が変わってるの?」と原因を追いにくいバグにつながってしまいます。

この記事では、Excel VBAのPublic変数の宣言方法、モジュール間で値を共有する基本、そしてPublic変数に頼りすぎない値の渡し方まで、初心者にも分かりやすく整理して解説していきます。

1. Excel VBAのPublic変数って何?

Excel VBAのPublic変数とは、標準モジュールの宣言セクション(プロシージャの外側、モジュールの一番上の部分)でPublicというキーワードを使って宣言する変数のことです。

普通、プロシージャの中でDimを使って宣言した変数は、そのプロシージャの中でしか使えません。

でも、Publicで宣言した変数は、同じVBAプロジェクト内の別モジュールからも参照できるので、複数の処理で同じ値を共有したいときに使われます。

VBAの変数は、宣言する場所とキーワードによって使える範囲が変わります。

– プロシージャ内のDim変数 → ローカル変数(そのプロシージャ内だけ)
– モジュール先頭のDimまたはPrivate変数 → モジュールレベル変数(そのモジュール内だけ)
– モジュール先頭のPublic変数 → プロジェクト全体で使える変数

この「使える範囲」のことを**スコープ**と呼びます。

Public変数はスコープが広いので、値の受け渡しが簡単にできる反面、「どの処理がいつ値を書き換えたのか分かりにくくなる」という注意点があります。

例えば、次のように標準モジュールの先頭でPublic変数を宣言します。

“`vb
Option Explicit

Public userName As String
Public totalAmount As Long
“`

こうしておけば、同じブック内のVBAプロジェクトにある他の標準モジュールから、userNameやtotalAmountをそのまま使えるようになります。

ちなみに、Public変数を使う場合でも、**Option Explicit**は必ず書いておきましょう。

これを有効にすると、変数名の入力ミスや未宣言の変数を使ったときにコンパイルエラーで気づけるので、意図しないバグを防ぎやすくなります。

2. Public変数を宣言してモジュール間で値を共有する基本

Public変数を使ったモジュール間の値渡しは、実際には「値を渡す」というより**「共通の変数を複数のモジュールから参照する」**と考えると理解しやすくなります。

たとえば、Module1でPublic変数を宣言して、Module2で値を代入して、Module3でその値を表示する、といった使い方ができます。

処理を複数の標準モジュールに分けている場合でも、同じPublic変数を見ているので、値の共有が可能になるわけです。

実際の例を見てみましょう。

**Module1:**
“`vb
Option Explicit

Public messageText As String
“`

**Module2:**
“`vb
Option Explicit

Sub SetMessage()
messageText = “処理が完了しました”
Call ShowMessage
End Sub
“`

**Module3:**
“`vb
Option Explicit

Sub ShowMessage()
MsgBox messageText
End Sub
“`

この例では、Module2のSetMessageでPublic変数messageTextに文字列を代入して、Module3のShowMessageでその値を表示しています。

messageTextはModule1でPublic宣言されているので、Module2にもModule3にも同じ変数として見えるんです。

小規模なマクロであれば、この書き方は直感的で分かりやすく、処理の流れもシンプルに書けます。

宣言する場所と変数名の付け方

ただし、Public変数はどこに宣言してもいいわけではありません。

基本的には**標準モジュールに宣言する**のが分かりやすいです。

また、変数名も用途が伝わる名前にすることが大切です。

たとえば、bufやtmpのような曖昧な名前をPublic変数にすると、後から見たときに「これ何の値?」と判断しづらくなります。

複数のモジュールで共有する変数ほど、次のような意味の分かる名前を付けましょう。

– currentUserName
– targetSheetName
– processResult

Public変数の値は残り続ける

もう一つ注意点があります。

Public変数は**プロシージャの実行が終わっても値が残る**ことがあります。

VBAの実行状態がリセットされるまでは、前回代入した値が残っている場合があるので、「最初は空のはず」と思い込むと予期しない結果になることがあります。

Public変数を使うときは、**処理の開始時に初期化する習慣**を持つと安全です。

文字列なら空文字、数値なら0、オブジェクトならNothingを設定するなど、開始時点の状態を明確にしておきましょう。

3. Public変数を使うメリットと注意点

メリット:コードが短く書ける

Public変数の最大のメリットは、**モジュール間で値を共有するコードを短く書ける**ことです。

引数を何度も渡したり、戻り値を受け取ったりしなくても、どのモジュールからでも同じ変数を参照できます。

たとえば、ユーザーフォームに初期値を渡したいときや、複数の処理で共通設定を使いたいときには、Public変数を使うと実装が簡単になります。

特に、学習段階や小さな業務マクロでは、処理の全体像をつかみやすいという利点があります。

デメリット:値が変わった原因を追いにくい

一方で、Public変数には明確なデメリットもあります。

**どこからでも書き換えられるため、値が変わった原因を追いにくくなります。

**

複数人で開発している場合は、同じ名前の変数を作ってしまったり、別の処理が意図せず値を変更したりする可能性もあります。

また、コード補完に常に候補として表示されるため、変数が増えるほど開発中の見通しが悪くなります。

Public変数は便利な共有場所である反面、**管理されていない共有場所**になりやすいんです。

Public変数を使うときのルール

Public変数を使う場合は、次のようなルールを決めておくと保守しやすくなります。

– **Public変数は必要最小限にし、何でもPublicにしない**
– **処理開始時に初期化し、前回実行時の値を残さない**
– **値を書き換える場所を限定し、参照だけの処理と分ける**
– **変数名には用途が分かる具体的な名前を付ける**

たとえば、税率やファイルパスのように処理全体で使う値をPublic変数にする場合でも、途中で頻繁に書き換える設計は避けたほうが安全です。

定数化できるものはPublic Constにする

値が固定でよいものは、**Public Const**を使って定数として宣言する方法もあります。

定数は実行中に値を書き換えられないため、誤代入によるバグを防ぎやすくなります。

“`vb
Option Explicit

Public Const TAX_RATE As Double = 0.1
“`

このように定数化できる値はPublic変数ではなくPublic Constにすることで、コードの意図が明確になります。

Public変数は「全体で使える便利な変数」ではありますが、**「全体から変更できてしまう危険な変数」**でもあります。

そのため、使う前に「本当にPublicである必要があるのか?」を考えることが重要です。

4. Public変数に頼らないモジュール間の値渡し

モジュール間で値を渡したい場合、必ずPublic変数を使わなければならないわけではありません。

むしろ、保守性を重視するなら、**引数や戻り値を使って値を渡す方法**が基本です。

引数とは、SubやFunctionを呼び出すときに渡す値のことで、戻り値とはFunctionの実行結果として返す値のことです。

この方法なら、**どの値がどこから来て、どこへ渡されるのかがコード上で明確**になります。

引数と戻り値を使った値渡し

たとえば、別モジュールのFunctionから計算結果を受け取る場合は、次のように書けます。

**Module1:**
“`vb
Option Explicit

Sub Main()
Dim price As Long
price = GetTotalAmount(1000, 3)

MsgBox price
End Sub
“`

**Module2:**
“`vb
Option Explicit

Public Function GetTotalAmount(ByVal unitPrice As Long, ByVal quantity As Long) As Long
GetTotalAmount = unitPrice * quantity
End Function
“`

この例では、Module1からModule2のGetTotalAmountを呼び出し、単価と数量を引数として渡しています。

計算結果はFunctionの戻り値としてModule1に返されます。

Public変数を使ってunitPriceやquantityを共有する必要がないため、値の流れが分かりやすくなります。

後からコードを読む人も、「この関数は単価と数量を受け取り、合計金額を返すんだな」とすぐに理解できます。

ユーザーフォームに値を渡す方法

ユーザーフォームに値を渡す場合も、Public変数だけが選択肢ではありません。

フォームを表示する前に、標準モジュール側からフォーム上のテキストボックスやプロパティへ値を設定する方法があります。

たとえば、TestFormのtbNameというテキストボックスに初期値を入れてから表示するなら、次のように書けます。

“`vb
Sub ShowInputForm()
With TestForm
.tbName.Value = “山田太郎”
.Show
MsgBox .tbName.Value
End With

Unload TestForm
End Sub
“`

この方法では、Public変数を使わずにフォームへ値を渡し、フォームで入力された値を表示後に受け取れます。

フォーム側では、ボタンが押されたらUnloadではなく**Hide**で一時的に非表示にしておくと、標準モジュール側から入力値を参照できます。

最後にUnloadしてフォームを破棄すれば、不要な状態を残さずに済みます。

フォーム内に処理を詰め込みすぎず、標準モジュール側で流れを管理できる点もメリットです。

クラスモジュールのPublic変数は別物

ちなみに、クラスモジュール内でPublicなメンバー変数を使うケースは、標準モジュールのPublic変数とは性質が異なります。

クラスのPublic変数は、そのクラスから作成したオブジェクトのプロパティのように扱われるため、プロジェクト全体で1つの値を共有するグローバル変数とは違います。

たとえば、1件分の顧客データや商品データを表すクラスで、NameやPriceをPublicにする設計は、用途によっては自然です。

ただし、大きな開発では**Property Get、Property Let**を使って値の取得・設定を制御するほうが安全です。

まとめ:使いどころを判断できるようになろう

Excel VBAのPublic変数は、宣言方法を覚えるだけなら難しくありません。

でも、実務で大切なのは**「使えること」よりも「使いどころを判断できること」**です。

小さなマクロで一時的に値を共有するならPublic変数は便利ですが、処理が増えるほど引数、戻り値、Private変数、定数、クラスなどを使い分ける必要があります。

まずはPublic変数のスコープとリスクを理解して、**値の流れが読みやすいコード**を書くことを意識してみてください。

そうすれば、後から修正しやすいVBAになります。

この記事が、Public変数の理解と使い分けの参考になれば嬉しいです!

広告