VBAの定数の使い方で、計算値を定数に入れることは可能ですか。
例えば、モジュール先頭に、
Option Explicit
Const TEISU_COUNT As Integer = Application.WorksheetFunction.CountA(Range("A1:IV1"))
と書き、その下に、
Sub TestTeisu()
MsgBox TEISU_COUNT
'↑定数式が必要です、のようなエラーが出ます。なぜでしょう?
'エラー時、「.CountA」にスポットがあたります。
'つまり、ここがダメということでしょうか?やはり、この点が動的だからでしょうか?
End Sub
と書いて、実行。
結果は、上述の通り、エラーとなります。
やはり、定数値には、固定的な数値(上記例では、Integer)や文字列を入れるべきなのでしょうか。
定数に入れることのできる値の注意事項について、
どなたかアドバイスして頂けますでしょうか。
宜しくお願い致します。
No.3ベストアンサー
- 回答日時:
#2の回答者です。
本当は、変数と定数の区別のつかない段階で、混乱するので、余計な話は聞かないで進めていったほうがよいのですが、一応、お答えしておきます。
定数は、変動したり値やプロパティを取得するものには使えません。だから、本来、比較のしようがありません。
グローバル変数のメリットとしては、一定の環境で、再取得することなく使えることです。主に、Auto_Open で取得して、最後まで使うことが多いです。グローバルにしておけば、他のプロシージャにでも、使えます。再取得する必要がないので、当然、処理スピードは上がります。
メモリについては、このレベルでは気にするほどのものはありません。String 型ですと、文字数に比例しますが、数値型は、仮にLong 型でも、4 Byte しかありません。Integer型は、2 Byte ですが、事実上、32ビットパソコンでは、4 Byte =32ビット分を使用します。メモリについては心配はほぼないと思います。処理速度の違いですが、定数と変数の違い自体は比べようもありませんが、再取得は別として、変数が100個も使うならともかく、その差は検知できないはずです。
グローバル変数のデメリットは、実は、マクロ稼働中にエラーが発生して、グローバル変数の内容がなくなってしまう、という問題があります。そうすると、以下のようなチェックコードが必要になるということがあります。
If g_Count =0 Then
Call RowCount
End If
'//
Public g_Count As Integer
Public Function RowCount()
g_Count = Application.WorksheetFunction.CountA(Range("A1:IV1"))
End Function
普通は、こんなことは気にしなくてよいのですが、複雑な内容のマクロですと、必要になることがあります。また、なるべく、変数の名称は、プロシージャ内の変数とは区別がつくようにしてやることがコツです。こういうマクロは、1~2年レベルの経験では使わないと思います。
>ある固定的な値を入れる容器として、
>定数を使った場合でも、
>また、グローバル変数を使った場合でも動く
具体的な状況が思い浮かびません。どちらでも動くから、定数を使うというものでもないように思います。
前回も書いたように、消費税や数式の係数に対して用いるというのが、基本です。
詳細な補足をありがとうございます。
定数とグローバル変数は、同じ土俵で比べられるものではないようですね。
用途が似ているようで似ていない、全くフィールドの異なる概念であるように思いました。
よって、両者のどちらを使うかで迷う、ということはない、ということなのでしょうね。
>具体的な状況が思い浮かびません。
苦し紛れに、具体的な状況を挙げさせて頂くと、
たとえば、
>グローバル変数のメリットとしては、一定の環境で、再取得することなく使えること
とありましたが、
定数では、またげないスコープに対し、オールラウンドに、ある特定の値を使い回したい場合、
各スコープで、毎回、定数宣言をするよりかは、
どこか1箇所でグローバル変数宣言をして、その特定の値を使うようにしたほうが、
「その特定の値 に種類が50ほどある場合」なんかには、
コードが短くなり、メリットがあるのかなぁ、なんて思いましたが、いかがでしょう?
その場合、
Public Sub Global_Var_Dim()
Public global_var01 as Single = 0.05
Public global_var02 as Single = 1.05
Public global_var03 as Single = 3.14
:
:
Public global_var48 as Single = 1.41421356
Public global_var49 as Single = 2.71828
Public global_var50 as Single = 1.7320568
End Sub
こんなプロシージャを、どこか1箇所で実行するようにします。
一方、上記を定数で処理するとなると、
50個の特定の値を、各スコープで毎回、宣言することになりますよね。
これを私は冗長と考えたわけですが、何か見落としなどはありますでしょうか。
※
まだVBA初心者であるため、文法的に変なことを言っているかもしれません。
考え方の大枠として、こんなことはできないだろうか~?といった話として、
解釈頂けると助かります。
もしまたよろしければ教えて下さい。
No.4
- 回答日時:
>定数では、またげないスコープに対し、オールラウンドに、ある特定の値を使い回したい場合、
>上記を定数で処理するとなると、50個の特定の値を、各スコープで毎回、宣言することになりますよね。
定数も変数も、基本的にはスコープは同じです。またげないということはありませんが、そこまでのレベルが必要になるというのは、入門の方からすれば、遥か彼方のテクニックだと思います。
Public global_Var(49) As Single '注:VBAでは、Single 型は慣例的にDouble型にすることが多い
'私は、こういう場合は配列に確保します。
Private Sub Global_Var_Dim()
global_var(0) = 0.05
global_var(1) = 1.05
global_var(2) = 3.14
・
・
・
・
・
End Sub
または、Long型の場合は、列挙型にすることが多いです。
しかし、実際問題として、あまり、公にしていないのですが、プロの作ったものは、この場合、アドイン(.xla)にして、シートにデータを置き、そこから取り出す書かたをする人が多いようです。秘匿性がないので、あまり格好良くないのですが、決め打ちでやってみると、取り出すことが可能です。Excel VBAというものは、そういうものだとするしかありません。それ以外の方法(暗号化)もあるようですが、私自身、それ以上のことはしたことがありません。そこまで必要とされないからです。
さらなる補足をありがとうございます。
>定数も変数も、基本的にはスコープは同じです。
あらら、では、私の挙げた例は適切ではありませんでしたね。苦笑
しかし、おかげさまで、
定数とグローバル変数の使い分けが少し分かったように思います。
ありがとうございます。
>シートにデータを置き、そこから取り出す書かたをする人が多いようです。
そういうテクニックもあるわけですね。
>'注:VBAでは、Single 型は慣例的にDouble型にすることが多い
>'私は、こういう場合は配列に確保します。
こちらも、勉強になりました。
メモリのことを気にして、できる限り、Doubleは使わずにSingleで確実に大丈夫な所はSingleで、
なんて私は考えていましたが、業界の慣例ではDoubleにすることが多いのですか~、始めて知りました。
それでは、定数をドッサリ使って、作業を再開したいと思います。
終始、丁寧に回答下さり、ありがとうございました。
No.2
- 回答日時:
元のコードからすれば、以下のようにするのが自然だと思います。
'//
Option Explicit
Public g_Count As Integer '←Global 変数の場合は、標準モジュールに置きます。
'モジュールレベルなら、Private m_Count As Integer
Sub TestMacro1() '←Global変数を使っている場合は、同じモジュールでなくても可能
g_Count = Application.WorksheetFunction.CountA(Range("A1:IV1"))
MsgBox g_Count
End Sub
定数というのは、固定値ですから、変動しないことが条件です。
例えば、消費税として、Const RATE As Double = 0.05 など、定数(Constant)を使います。ワークシートの変動する条件の値を取る場合は、変数(Variable)です。
.CountAなどを用いて計算した値を使い回す際に使用する「データの入れ物」は、
定数ではなくグローバル変数が良さそうですね。
当初、私は、例えば、消費税のような定数で良いようなものまで、
グローバル変数に入れて、固定的なグローバル変数というような扱いで、
まるで定数のように使っていたのですが、
「定数」そのものの存在を、ごく最近知りましたので、
定数にできるものは全て定数にしてしまおうと考え、
今回のような疑問にぶち当たりました。
定数で問題ないものを、仮にグローバル変数に入れて使う場合に考えられるメリット、デメリットがあれば、
教えて頂けると嬉しいです。
(どなたでも結構ですので、心当たりのある方、お願い致します。)
定数の場合、コード中に値が変更されてしまわない、
というメリットがあるように思いますが、それを踏まえた上で、
ここで私が知りたいメリットとは、具体的には、「処理速度」の面のメリットです。
メモリの食い、なども気になります。
ある固定的な値を入れる容器として、
定数を使った場合でも、
また、グローバル変数を使った場合でも動く
という場合には、
やはり、グローバル変数ではなく、定数の方を使うべきなのでしょうか。
変なことを質問しているとは思いますが、
もしまた機会がございましたら、教えて下さい。
No.1
- 回答日時:
>やはり、定数値には、固定的な数値(上記例では、Integer)や文字列を入れるべきなのでしょうか。
その通りです。
使えるのは、リテラル値、その他の定数、Isを除く算術演算子や論理演算子を組み合わせた式です。
シート関数の利用はもちろんシート内容も参照することはできませんし、VBAの関数も使うことはできません。
たとえば、
Const a As Single = 5.5 * 3
Sub Test()
MsgBox Int(a)
End Sub
は大丈夫ですが、
Const a As Single = Int(5.5 * 3)
Sub Test()
MsgBox a
End Sub
はだめです。
大変わかりやすい回答をありがとうございます。
>使えるのは、リテラル値、その他の定数、Isを除く算術演算子や論理演算子を組み合わせた式
上記に気をつけて、定数宣言をしていこうと思います。
分かりやすい具体例もありがとうございました。
お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!
このQ&Aを見た人はこんなQ&Aも見ています
-
あるあるbotに投稿したけど採用されなかったあるある募集
あるあるbotに投稿したけど採用されなかったあるあるをこちらに投稿してください
-
フォロワー20万人のアカウントであなたのあるあるを披露してみませんか?
あなたが普段思っている「これまだ誰も言ってなかったけど共感されるだろうな」というあるあるを教えてください
-
映画のエンドロール観る派?観ない派?
映画が終わった後、すぐに席を立って帰る方もちらほら見かけます。皆さんはエンドロールの最後まで観ていきますか?
-
海外旅行から帰ってきたら、まず何を食べる?
帰国して1番食べたくなるもの、食べたくなるだろうなと思うもの、皆さんはありますか?
-
天使と悪魔選手権
悪魔がこんなささやきをしていたら、天使のあなたはなんと言って止めますか?
-
[VBS]変数を定数に変換する方法を教えて下さい。
Visual Basic(VBA)
-
ExcelのVBA。public変数の値が消える
Visual Basic(VBA)
-
VBA Constの指定シートのセルを指定する方法
Visual Basic(VBA)
-
-
4
Excel-vba 文字列と変数を連結して更に変数として扱いたい
その他(プログラミング・Web制作)
-
5
VBAでループ内で使う変数名を可変にできないか。
Visual Basic(VBA)
-
6
エクセル:マクロ「Application.CutCopyMode = False」って?
Excel(エクセル)
-
7
【エクセルのマクロ】クリップボードのbitmapをフォームに表示させたい
Visual Basic(VBA)
-
8
再度,ExcelVBA,public変数が消える
Visual Basic(VBA)
-
9
Excel VBA 定数にオブジェクトを指定したい
Visual Basic(VBA)
-
10
VBAでブックを非表示で開いて処理して閉じる方法
Excel(エクセル)
-
11
worksheetFunctionクラスのVlookupプロパティを取得できません エラーへの対応
Visual Basic(VBA)
関連するカテゴリからQ&Aを探す
おすすめ情報
- ・漫画をレンタルでお得に読める!
- ・人生のプチ美学を教えてください!!
- ・10秒目をつむったら…
- ・あなたの習慣について教えてください!!
- ・牛、豚、鶏、どれか一つ食べられなくなるとしたら?
- ・【大喜利】【投稿~9/18】 おとぎ話『桃太郎』の知られざるエピソード
- ・街中で見かけて「グッときた人」の思い出
- ・「一気に最後まで読んだ」本、教えて下さい!
- ・幼稚園時代「何組」でしたか?
- ・激凹みから立ち直る方法
- ・1つだけ過去を変えられるとしたら?
- ・【あるあるbot連動企画】あるあるbotに投稿したけど採用されなかったあるある募集
- ・【あるあるbot連動企画】フォロワー20万人のアカウントであなたのあるあるを披露してみませんか?
- ・映画のエンドロール観る派?観ない派?
- ・海外旅行から帰ってきたら、まず何を食べる?
- ・誕生日にもらった意外なもの
- ・天使と悪魔選手権
- ・ちょっと先の未来クイズ第2問
- ・【大喜利】【投稿~9/7】 ロボットの住む世界で流行ってる罰ゲームとは?
- ・推しミネラルウォーターはありますか?
- ・都道府県穴埋めゲーム
- ・この人頭いいなと思ったエピソード
- ・準・究極の選択
このQ&Aを見た人がよく見るQ&A
デイリーランキングこのカテゴリの人気デイリーQ&Aランキング
-
C言語 exitの使い方
-
フォームを開くときに、コンボ...
-
VB6.0-整数と余りを求める
-
数字の位ごとの値を表示するプ...
-
【C++/CLI】String型文字列の位...
-
フリーランタイマーの時間差分...
-
Excel-vba 文字列と変数を...
-
1つ前の値を変数に保存する方法
-
VBA コンボボックスの値をスピ...
-
バッチファイルで正規表現を使...
-
VBAで配列のNULL判定
-
DWORDって
-
C#の問題で2つの整数a,bの...
-
データ構造のmapとは?
-
VBAのチェックボックス結果を集...
-
VBからストアドの動的SQLを呼ん...
-
(初心者)乱数のことで
-
UWSCのcallについて
-
DataGridView 複数行同時変更...
-
何種類の値があるかを調べる方...
マンスリーランキングこのカテゴリの人気マンスリーQ&Aランキング
-
C言語 exitの使い方
-
フォームを開くときに、コンボ...
-
足して100になるような乱数のア...
-
VB6.0-整数と余りを求める
-
Excel-vba 文字列と変数を...
-
C#で動的にコントロールを取得...
-
DWORDって
-
DataGridView 複数行同時変更...
-
VBAで配列のNULL判定
-
ラジオボタンの値の取得につい...
-
4択問題のプログラムでランダム...
-
VBAの定数の使い方で、計算値を...
-
数字の位ごとの値を表示するプ...
-
VBA コンボボックスの値をスピ...
-
C言語でCLAMP(a,b,c)
-
1つ前の値を変数に保存する方法
-
世界のナベアツ
-
データ構造のmapとは?
-
10進数をアスキーコードに変換
-
【C++/CLI】String型文字列の位...
おすすめ情報