vba 64bit 型が 一致 しま せん 6

0 0

* Declare文の引数の型をLongPtrに変える

#End If, Sub GetFolderName() WinAPIを64bitに対応しようとした時に絶対に覚えなくてはならないのがLongPtrである。, Declare文の64bit対応に関しては以前次のような記事を書いたが、LongPtrの置き換えの考え方に関しては一切説明できなかった。, 今回は64bit対応のためにPtrSafe/LongPtrが実装された経緯について、私が想像したことを説明する。, あくまで個人的に「たぶんこうだったんだろうな」と理解したまでで、公式に得た情報ではないので注意するように。, 例えば、あるウィンドウをアクティブに切り替えるAPI:SetForegroundWindowのDeclare文は次のようになる。, 多くのVBAではコンパイルエラーがあっても実際に流入する瞬間までエラーは出ないのだが、宣言セクションなどの全体に影響する部分のコンパイルエラーがある時は、一切のVBAの実行ができなくなるように出来ている。, 詳しくは後ほど説明するが、LongPtrへの置き換えを行わなければVBA実行中にExcel自体がクラッシュすることになるので「ちゃんとチェックした」ということをコンパイラに事前に伝えるために生まれたのが「PtrSafe」である。, 64bit環境では、一つでもPtrSafeが不足しているとプロジェクト全体が64bit非対応とみなし、そのAPIを使用するか否かに関わらず一切のプロシージャの実行を認めないというかなり厳しい制限を敷いている。, もし実行できてしまったらExcelがクラッシュすることになるので、そのくらい厳しい制限で丁度よいと私は考えている。, というわけで、「PtrSafeを書く」たったそれだけで「コンパイルエラーは出なくなる」, ちなみに問題となるのはLongとは限らなくて、StringやAnyなどからLongPtrに置き換えなければならないこともあるが、ややっこしいので事例紹介はLongだけにする。置き換えが必要なパラメータの8割方はメモリ・ポインタ・ハンドル関係なので、これらは(たぶん)全てが修正対象となる。, PtrSafeを付けるのは「ちゃんとチェックしたよ!!!」と宣言するために書くべきなのだが、現実は「とりあえず書いとけ」状態になっている。コンパイルが通らないことには始まらないので、型の変更が後回しになるのは仕方がないのだが、それではMicrosoftがこのような安全措置を取ってくれたのが意味を成さない。, LongPtrの話をする前に、64bitで増えたLongLongが何者なのか知らなければならない。, 昭和生まれの方なら、32bit時代のメモリ制限には苦しめられた人が少なくないのではないだろうか?(尤も、私は平成生まれだが・・・), 32bit OS(XP)ではメモリを3GB強しか認識できなかった。2GBx2本を搭載して4GBにしても、実際に使えるのは3.3GBとかその程度で残りは使用できなかった。, 32bitアプリでは1つのプロセスで2GBまでしか使用できず、メモリの食う画像処理では重い足かせとなっていた。, これは64bit OSでも同じことで、32bitアプリを動かす時は2GB制限がかかっている。動画編集ソフトaviutlなどで有名だ。高負荷処理を行うアプリは早々に64bit化されており、ついに一般向けのExcelにまで降りてきているのが現状である。, さて、OSかアプリかの違いはあるものの、64bitに変化したことで得られるメリットは、このメモリ制限の撤廃だ。64bit化されたことで、今後数百年は使い切れないほど無限のメモリを使う事ができる。, なぜ使えるメモリの容量が増えたのかと言えば、メモリアドレスの桁数が増えたからなのだ。, 32bit環境では2進数で32桁までのメモリアドレスしか格納できなかった。2の32乗=4,294,967,296=4GiBである。, 従来の32bit VBAでは、このメモリアドレスを格納するデータ型としてLong型を使用してきた。*2, ところが64bit環境では、2進数で64桁まで格納できるようになり、もはや使い切れないくらい巨大な空間にアドレスを振れるようになった。, それはつまり桁数が2倍に増えているので、変数の大きさも2倍にしないといけないということを意味する。, だから、64bit環境のメモリアドレスが格納できるように、Long型の2倍の桁数を持つLongLong型が出来た。, 環境に応じてデータ型変化するLongPtrがあると、コードが非常にスッキリするのだ。, 例えば、https://docs.microsoft.com/ja-jp/windows/win32/api/winuser/nf-winuser-setforegroundwindow によれば、SetForegroundWindowは次のように規程されている。, (LongLongが無い)32bit環境のためにWin64で分岐し、(PtrSafe・LongPtrが無い)Excel2007以前のためにVBA7で分岐しなければならない。, 3つ目は古いExcel用のため切り捨てられるとしても、最初の2つは書かないといけない。, これが未来永劫続くを防ぐために、MicrosoftはLongPtrを実装したのではないかと考られる。, LongPtrはExcelの環境が32bitか64bitかで、実体の型が変化するという特別なデータ型である。, 困ったことにLongPtrが原因で本質を理解しずらくなってしまっているが、すべきことは大きく分けて2つある。, まずは宣言側の修正が必要だ。 非力な私には「APIを呼び出すときはハンドルやポインタの型を変える必要があります」とは言うものの簡単ではありません…サンプルコードには本当に感謝しています。    ulFlags As Long     End With そのとき図形を削除するのではなく、図形の表示・非表示を切り替えることができ... 条件分岐で処理を実行させるには、If~Thenステートメント以外にもSelect Caseステートメントがあります。 64bit環境で以下のソースを実行すると★★★'の部分で型が違います'エラー.    iImage As Long #Else    ' Downlevel when using previous version of VBA7  Public Const WM_USER = &H400 「#」はファイル番号の意味    hOwner As LongPtr * Declare文の引数でType(ユーザー定義型)を参照渡ししている場合、Typeのメンバの型も適時LongからLongPtrに変える, この修正に関しては、Win32API_ptrsafe.txtからコピペするなり、原典資料を読んで仕様から置き換えれば比較的容易に対応できる。, この例くらいなら暗黙の型変換で問題なく動作する可能性が高いが、場合によってはコンパイルエラーが出たりExcelが瞬時にクラッシュしてしまう。, API関数の戻り値がLongPtrとなる場合も、代入時に修正しなければコンパイルエラーー「型が一致しません」が出る。, ここまでは、コンパイルエラーに頼りながら修正していけば、そこまで苦労せずに対応できる。, VBAには符号なし整数(Unsigned Int/Long)型がないので、厳密にはLongを使うと不味い場面がある。, コンパイル時点では検知不可能なので、VBA実行中に思ったとおりに動かなくて問題が判明する。, コード上で自力で修正を加えたり、あえてCurrency型を活用するという方法がある。, LongLongのポインタを渡すべきところでLongのポインタを渡したら、API内部でLong以上のブロックのメモリに書き込むことになるためメモリが破壊されてしまう。, だからStrPtrとかVarPtrとかで渡しているところは全部チェックしないといけない。, 32bit環境では全く問題ありませんが、64bit環境では「クラッシュ」という形で問題が現れます。, LongをLongLongに入れることはできるが、LongLongをLongに入れるのは不可能です。, Long型引数を持つAPIにLongPtrで宣言した変数を渡すとコンパイルエラーが出ます。, また、一旦LongPtrに修正したものの、後日適切なコードに直すためLongに戻すという無駄な労力が発生します。, API側で書き込む構造体の大きさは明確に決められているので、LongにすべきところをLongLongにしてしまったら大きさが仕様と変わってしまう。, 当然、そのような構造体を渡したら、意図しないところに謝ったデータを書き込むのでクラッシュする。, 32bit環境でLongPtrはLongとして動作する。つまり全部LongPtrに変えてもエラーが出るわけがないのだ, 面倒かつ財布に厳しい話ではあるが、APIを使う人は最低でも64bit環境で開発するか、両方を保有してテストを通す必要がある。, 2013以降のOfficeであれば、オンラインからダウンロードしてインストールできるので、32bitはアンインストールして64bitに入れ替えましょう。, https://twitter.com/KotorinChunChun/status/1274154632244166656?s=20, Win64APIは文字通り64bit用のAPIなんだけど、ほぼ全ての関数は32と共通のもので、引数や戻り値の型が64bit対応のために変化しているだけという印象。 特にメモリアドレスの空間が拡大された影響が大きくて、例えばVBAではポインタを示す箇所が全部LongからLongLongに変わっている。 だが・・, 32bit/64bit両対応のために、そっくりなDeclare文を2回も書かないのはアホらしい・・という理由から、VBAでは LongPtr とかいう素晴らしい型が追加されており、ほぼ全てのWinAPIは書き直す必要が無くなった。 これが原因で、OSの仕組みの本質を理解出来ないで使う人が多くなっていると思う。, 64bitでPtrSafeを書かされるのは、この「引数・戻り値の型」をちゃんと64bit対応のためにチェックしましたよ!というプログラマの意図をコンパイラに報告させる行為だと思う。 そうすることで、PtrSafeが無い文は64bit未対応という判定を、コンパイル時点でチェックでき、未対応のVBAは一切動かない。, もし「PtrSafeを書きなさい」というルールがなかったら、VBAは実際に関数を実行してメモリ破壊が起こるまで、間違っていることが分からない。 というか、ExcelまたはWindowsがクラッシュする。 実際に初学者が、本質を理解せずPtrSafeだけ追記してLongPtrに変えなかった場合に起こる現象そのまんま, かくゆう私も、ここまで理解するのに何百回もExcelをクラッシュさせたという経験がある。(トライアンドエラーの境地) それぞれのAPI(関数)をどう書き換えるかは、仕様書を読めば分かる。が、読むのは大変なので、Microsoft公式の Win32API_PtrSafe.txt からコピーせよ。, https://docs.microsoft.com/ja-jp/office/client-developer/shared/compatibility-between-the-32-bit-and-64-bit-versions-of-office, Win32API_PtrSafe.txt に書かれていない関数の宣言文がほしい時は、Google先生に聞いてみると良い。 例:"Declare PtrSafe Function GetDeviceCaps" ※ダブルクォーテーションで囲うのを忘れないこと。 PtrSafeのおかげで64bit対応版だけに絞って検索出来るので、とても都合が良い。, でも、ググって出てきた宣言文が仕様どおりに書かれている保証は無い。 とりあえずの参考には良いのだけど、ちゃんと複数バージョンでテストを通しておくとか、関数名で調べて仕様通りの型になっているかチェックしないとあぶない。, CreateFileAをCreateFileWに置き換えるために、ちょっと苦労した話。, https://twitter.com/KotorinChunChun/status/1275591987022856193?s=20, 以前、整数型の速度を比較した結果、64bitではLongLong(LongPtr)を使うのが一番高速という話。, ※ちなみに、私の説明している方法であれば32bit環境に持っていって動かないことはまず無い。(もちろん0じゃないのでテストはすべきだが、コンパイルエラーで検知できるレベルに抑えられる。), *1:「アレヤコレヤで4GBから更に削られて、3GBの壁や2GBの壁があった」というイメージで、私はなんとなく理解している。, *2:厳密にはVBAコンパイラの開発言語はVBAでは無いので、同じメモリサイズを持つデータ型に当たる, なお記事の元ネタは大抵はTwitterで呟いてます。良ければフォローしてあげてください。, 今回は64bit版VBAの整数型で使えるIntergerとLongとLongLongの…, WinAPIの64bit化で出てくるPtrSafe、LongLong、LongPtrってなんなのさ?, 「アレヤコレヤで4GBから更に削られて、3GBの壁や2GBの壁があった」というイメージで、私はなんとなく理解している。, 32bit環境しかないけど64bit対応できたつもりなので、PtrSafe付けてもいいですか?, https://docs.microsoft.com/ja-jp/windows/win32/api/winuser/nf-winuser-setforegroundwindow, Excelシートのデータ範囲を2次元配列に格納するVBA汎用関数を作ってみた Part2, チャットのEnterキーの挙動を徹底調査してみた。~改行キーと送信キーは統一すべきである~, ExcelにGoogle Spreadsheetを読み込むVBA汎用関数を作ってみた.         Exit Sub  End Type End Function, #Else    ' Downlevel when using previous version of VBA7, Public Function BrowseCallbackProc(ByVal hWnd As Long, ByVal uMsg As Long, ByVal lParam As Long, ByVal lpData As Long) As Long  ''コールバック関数 アウトラインは行や列の表示・非表示を切り替えるために使います。

        GetDirectory = Left(pPath, pos - 1) 尚、デバッグ時に「Private Function FP_BrowseCallback()」で「VBA オートメーションエラー(強制終了)」が発生するなどにてギブアップです。  Public Const BFFM_INITIALIZED = 1 サポートの受け方およびフィードバックをお寄せいただく方法のガイダンスについては、, Office VBA のサポートおよびフィードバック, 以前のバージョンのドキュメント.         .lpfn = FARPROC(AddressOf BrowseCallbackProc)

   lpszTitle As String

    Dim bInfo As BROWSEINFO, pPath As String     Dim R As Long, X As Long, pos As Integer  

   ulFlags As Long  Public Const BFFM_INITIALIZED = 1         If IsMissing(UserPath) Then  Private Declare Function SendMessage Lib "user32" Alias "SendMessageA"  (ByVal hWnd As Long, ByVal wMsg As Long,  ByVal wParam As Long, lParam As Any) As Long  Public Const BFFM_SETSELECTIONA = (WM_USER + 102) kenjinoteさんご教授本当にありがとうございました。, kenjinoteさん早速のご回答ありがとうございます。 64 ビット バージョンの Office 2010 アプリケーションで VBA マクロを実行するときに発生する「型の不一致」エラー メッセージが修正されます。この問題は、32 ビットのバージョンの Office アプリケーションでは正しく動作する VBA マクロに影響します。 配列を宣言したときにインデックス番号を「1」から始まるように設定する方法は... みなさんはVBAでアウトラインレベルやアウトラインのクリアを行っていますか?     End If         .pidlRoot = &H0         MsgBox buf End Function, 申し訳ありません。リクエストされたコンテンツは削除されています。すぐに自動的にリダイレクトされます。.     pPath = Space$(512)    pidlRoot As Long         pos = InStr(pPath, Chr(0)) Office VBA またはこの説明書に関するご質問やフィードバックがありますか?. Excel2013(32bit)で運用していた「フォルダ参照のダイアログ」を Excel2013(64bit)で運用しようとしたら、下記の「★★★」示しヶ所でコンパイルエラー「型が一致しません」が発生します。 非力にて対処方法が解りません…ご教授よろしくお願いいたします。     X = SHBrowseForFolder(bInfo)         End If

ギター ドレミ コード 8, ホットプレート 出しっぱなし レシピ 11, ボナンザ 将棋 ダウンロード Mac 18, 寄付 お礼状 コロナ 16, Nhk 宝塚 放送予定 7, 泡沫の夏 2018 感想 11, アコギ 洋楽 女性 6, 宝塚音楽学校 文化祭 2020 21, フルーツバスケット 声優 比較 12, サガミオリジナル クイック 違い 14, 流れ星 今日 見た 18, 渡辺徹 息子 アナウンサー 5, ライム フロウ バース 12, クリープ 金属 メカニズム 15, ドラ恋 まさき インスタ 7, 小説 時間経過 表現 8, The Glory Jリーグ ダウンロード 24, ハラスメント ポスター 労働局 13, アメリカ 蜂 種類 28, リッチマンプアウーマン 5話 ネタバレ 14, さんま 画廊 作品 11, クラウドワークス データ入力 単価 5, ヨドバシ 領収書 再発行 店舗 37, ホテル三日月 富士見亭 ブログ 13, クラーラ ペタッチ スカート 4, How Many Peopleの後 12, 為替差損益 仕訳 決算 5, 在宅 ワーク アクセサリー 作り 大阪 5, エンペラーギア シリアルコード 拡散 59, 家事ヤロウ 卵 醤油 7, 大宮 氷川神社 ライブカメラ 20, 猫よけ 効果絶大 ブログ 8, お酒 名言 面白い 7, 古畑任三郎 第2シリーズ 9話 権利 5, ゲオ Dvd100 円 10, 遊戯王 レガシーオブザデュエリスト テンポ 5, 不知火型 雲龍型 違い 4, 軽井沢 川上庵 メニュー 6, 江幡塁 三浦 春 馬 21, たまごっち み ー つ 何歳まで 生きる 6, 星 ドラ レア 鍵 4, 弁護士 高林鮎子 再放送 18, 中華料理 種類 一覧 10, 2009 ヤンキース なんj 9, カミラ ジョルジ ラケット 2020 22, 30過ぎて結婚 できない 女性の共通点 6, ミラティブ 友達配信 Ipad 26, Chr 特別仕様車 2020 51, Fallout76 リス 場所 5, 道路 緩和曲線 計算 5, 王家の愛 侍女と王子たち 原題 7, 杉村太蔵 子供 何人 16, ポケモンgo 無料レイドパス5枚 タイムゾーン 6, グラブル 闇ソルジャー バレット 34, 吉田拓郎 オールナイトニッポン 志村けん 25, 俺のキッチンスタジアム クリスマス 動画 16, 漆黒の追跡者 動画 Kissanime 32, ミチシルベ オレンジレンジ Mp3 8, 即日 入金 在宅 51, マルイ ガバメント 組み立て 5, 楽天 怪文書 なんj 11, Tokyo Go 歌詞 和訳 11, ジャンプ サッカー漫画 打ち切り 5, シャオ ユーウェイ インスタ 13, イルカ クジラ シャチ 仲間はずれ 5, パナソニック 浴室 マグネット 10, 平良 西武 なんj 4, Zelo 法律事務所 年収 28, Angela Atsuko 歌い方 15, マイクラ Ps4 スキン 消え た 17, 腓骨神経麻痺 低周波 効果 53, Destiny2 シーズン9 勝利の道のり 4, The D Motion 歌詞 変わった 6, コードブルー1 動画 Dailymotion 18, ディスカバー ディスカバリー 違い 8, Drm ベース 顔 4, Windows10 Hp Vpn 接続できない 8, 太宰治 身長 体重 57, マツエク 浜松 Coco 5, Oh My God カナルビ 8, 革靴 ハーフラバー 自分で 20, マリオカート ウデマエ チャレンジ 5, 尾 車 部屋 事件 4, ,Sitemap

View all contributions by

Leave a reply

Your email address will not be published. Required fields are marked *