VBA 32Bit版と64Bit版でDeclareステートメントの宣言を分ける方法 - Office 2010,2013
Office VBAで32Bit版と64BitでDeclareステートメントの宣言を分ける方法です。
ここではOffice 32Bit 版と 64Bit 版の違いや、32Bit 版なのか、64Bit 版なのかを判別する方法をサンプルソースで紹介しています。Office 32Bit 版と 64Bit 版の違い
MS Office は、Version2010 より、32Bit 版と 64Bit 版がリリースされました。
64Bit 版 Office では、32Bit 版に比べて使用できるメモリ容量が大きくなり、2GB を超えるサイズのファイルを扱うことができるようになりました。
これに伴い、VBA も VBA7 (Microsoft Visual Basic for Applications 7.0) にバージョンアップされました。
64Bit 版では、ポインターやハンドルのサイズが 32Bit 版に比べて大きくなったため、Long 型を使用すると予期しないエラーが発生する可能性があります。
そのため、Office 2010 以降ではその問題に対応した新しいデータ型として、LongPtr 型(ポインターデータ型)と LongLong型(64Bit 数値型)が追加されています。型変換するための CLngPtr() や CLngLng() も追加されています。
64Bit 版では、Declare ステートメントを使って Windows API を呼び出す場合、これまで使っていた Long 型を適切な形で置き換える必要があります。そうなると、32Bit 版なのか、64Bit 版なのかを判別する方法が必要になりますね。
Office 2010 以降、VBA7 と Win64 という条件付きコンパイル定数が追加されました。VBA7 は VBA のバージョンを区別するもので、Win64 は 32Bit/64Bit を区別するために利用します。
また、64Bit 版では Declare ステートメントに PtrSafe 属性がないとコンパイル時にエラーが発生します。このエラーの解決方法は「[このプロジェクトのコードは、64ビット・・Declare ・・]エラー解決方法 Excel VBA 2010 2013」のページで詳しく紹介していますので参考にしてみてください。サンプルソース
それでは、実際のソースをみてみましょう。
#If VBA7 And Win64 Then
' 64Bit 版
Private Declare PtrSafe Sub CopyMemory Lib "kernel32" Alias "RtlMoveMemory" (Destination As Any, Source As Any, ByVal Length As LongPtr)
#Else
' 32Bit 版
Private Declare Sub CopyMemory Lib "kernel32" Alias "RtlMoveMemory" (lpvDest As Any, lpvSource As Any, ByVal cbCopy As Long)
#End If
32Bit 版/64Bit 版だけを区別する場合は #If Win64 Then
を利用します。
参考サイト
・Office 2010 の 32 ビット バージョンと 64 ビット バージョンとの互換性
http://msdn.microsoft.com/ja-jp/library/office/ee691831(v=office.14).aspx
既存の 32Bit版 で作られた VBA プログラムは、その多くが 64Bit 版では動作しません。いづれ 64Bit 版の波が訪れ移行されていくのでしょうが、現時点ではまだまだ多くの企業様で 32Bit 版が利用されているのも事実です。64Bit 版の Office を導入する際は、この辺りの問題も含め、よく検討する必要があると思います。
追記
ご質問をいただいたので追記しておきます。
以下の画像は、Excel 64ビットでVBAのソースを開いた状態です。32ビットの記述は赤字でエラーのように表示されます。しかし、条件付きコンパイル関数のおかげで、32ビットの記述があってもコンパイルエラーにはなりません。
上図は64ビット版Excelで表示した場合。32ビット版の記述は赤字になるがコンパイルエラーにはならない。
このため、Excelを開いた直後から64ビット版のプログラムが利用できます。
おつかれさまでした。