私が目にする最大の問題は、またはSingle
の代わりに使用することです。素数は正の整数であり、10進値のコンテキストでは考えられません(私が知る限り)。したがって、シングルを使用し、それらを分割されたintと比較することにより、厄介なエッジケースのルーティングエラーが発生する可能性があります。Integer
Long
この行If N / D = Int(N / D) Then
は、数値が素数であるかどうかを確認するために不適切な方法を使用しています。浮動小数点数(この場合はシングル)を除数で割るたびに、10進数の余りがある場合、その余りの整数変換は等しくないと想定しています。ただし、回答を比較しようとすると、浮動小数点数で丸め誤差が発生することがあります。一般に、数値を比較する方法として浮動小数点から整数への変換を使用しないようにすることを学びました。
代わりに試すことができるコードを次に示します。注意すべき点:
- NとDのタイプを変更して、シングルではなくロングに変更しました。これは、浮動小数点ではなく、丸め誤差が発生する可能性があることを意味します。
- また、セルの値を明示的にlongに変換しました。このようにして、浮動小数点型を使用していないことがコードでわかります。
- 比較のために、の余りをで割っ
Mod
た値を返すを使用しました。余りが0の場合、trueを返し、素数がないことがわかります。(注:剰余は、除算の結果の整数値のみを返す、とともに使用されることがよくあります。 通常、整数型の正確な除算で使用されます。この場合は非常に適切です。N
D
\
Mod
\
- 最後に、比較されている実際の数を表示するようにメッセージボックスを変更しました。セル内の数値は変換されるため、ユーザーが浮動小数点値を入力すると、それが何に変換されたかを確認するのに役立ちます。
また、数億の数に達すると、このコードはコードよりもはるかに高速に実行されることに気付くでしょう。'
Sub GetPrime()
Dim N As Long
Dim D As Long
Dim tag As String
N = CLng(Cells(2, 2))
Select Case N
Case Is < 2
MsgBox N & " is not a prime number"
Case Is = 2
MsgBox N & " is a prime number"
Case Is > 2
D = 2
Do
If N Mod D = 0 Then
MsgBox N & " is not a prime number"
tag = "Not Prime"
Exit Do
End If
D = D + 1
Loop While D <= N - 1
If tag <> "Not Prime" Then
MsgBox N & " is a prime number"
End If
End Select
End Sub
注:プロシージャの名前をに変更しましたGetPrime
。あなたのコードでは、あなたは持っていました:
Private Sub CommandButton1_Click()
上記の行では、プロシージャ(メソッドとも呼ばれる、または単にsubと呼ばれることもあります)を定義しています。この単語Sub
は、値を返さないコードでプロシージャを定義していることを示します。(場合によっては、のFunction
代わりに単語が表示されることがありますSub
。これは、プロシージャがなどの値を返すことを意味しますPrivate Function ReturnANumber() As Long
。)プロシージャ(Sub
)は、呼び出されたときに実行されるコードの本体です。Sub
また、ExcelマクロはプロシージャとしてVBAに保存されます。
コード行では、はプロシージャCommandButton1_Click()
の名前です。ほとんどの場合、これはExcelスプレッドシートにボタンを追加することによって自動的に作成されました。ボタンがExcelスプレッドシートに関連付けられている場合、CommandButton1_Click()
ボタンが押されるたびに実行されます。
コード内で、プロシージャ の範囲Private
を示します。一般に、プロシージャは、それが存在するモジュールまたはクラスの外部で呼び出すことができないことを意味します。私のコードでは、別のコードモジュールから呼び出したい場合があるため、省略しました。Private
Private
GetPrime
コメントで、私のプロシージャの名前をからに変更する必要があると述べましGetPrime()
たCommandButton1_Click()
。それは確かに機能します。ただし、以下のように、内部GetPrime
から単純に呼び出すこともできます。 CommandButton1_Click()
Private Sub CommandButton1_Click()
'The following line of code will execute GetPrime() '
'Since GetPrime does not have parameters and does not return a value, '
'all you need to do is put the name of the procedure without the () '
GetPrime
End Sub
'Below is the entire code for the Sub GetPrime() '
Sub GetPrime()
'The body of the code goes below: '
' ... '
End Sub
これがVBAについて少し説明し、理解を深めるのに役立つことを願っています。