October 05, 2003VBAで泣かないために[Computer]
バイトで現在、VBA(Visual Basic for Applications)っていうのを書いてます。いわゆる、あれですよ、ExcelのMacroとか。で、やっていることはデータをグラフィカルに表におこしたりすることなわけで、一見猫作業=繰り返しやりつづける(どっちかっていうとハムスター作業かも)にみえるわけですが、いかんせんVBAっていうのが非常に詐欺的な言語(言語としても認めたくないぐらい)であるため、死にそうになっています。ってことで今回の御題はすばり『VBAで泣かないために(もう結構泣いたよぅ…)』。 VBAっていうと一般的な使い方はどうもExcelの『マクロでポン機能(マウス操作とかキー操作とかをマクロとして記録してくれるやつ)』をプラモデル的に組み合わせて使っている人が多いようです(もちろん、普段自分もこういう使い方してマクロ作っています)が、今回の作業がデータの構造をきちっととらないとあとあと破滅的になる(データベースからデータをひっぱってきているのです)ものだったので、今回はオブジェクト指向的にクラスモジュールなるものを使ってみました。クラスモジュールの使い方とかは他の人が細かく解説してくれていると思う(なんて無責任な…)ので、今回はずばり、プログラマーなあなたにおくる、VBAでは『クラスモジュール使ってオブジェクト指向やろうとしたのに、そんなことできないの、なんでやねん!!(ぶちっ)』特集といきたいと思います。実際あれができて当然と思い込んで泣かされたことが多数あるので、これは『VBAで泣かないために』っていう御題にぴったりかと思います。 まず当然のごとく、ポリモーフィズムがありません。ポリモーフィズムっていうのは、簡単にいえば、例えば同じ名前で引数の数や種類が違っていると違うものとして識別してくれる機能です。これよって、同じ名前でいくつも関数をつくって場面に応じて使い分けるといったことが普通のオブジェクト指向言語ならできるのですが、できません。もしどうしてもやりたいならVaraint型とかで引数をとって中でひたすら分岐しまくる、という手口を使うしかないんじゃないでしょうか? 次にコンストラクタがいけてません。コンストラクタであるClass_Initialize()は予約されていて、できるということとといえば、内部のオブジェクト変数を初期化するくらいです。しかもそのときはSet hoge = New Collectionみたいな感じでやるんですが、Setってなんなんですか?それゃ、Javaみたいにプリミティブ型とオブジェクト型ではっきりわかれてて、値を代入しているのか、参照を代入しているのか常に意識しなければならない言語ならちょっぴり仕方ないと思うけど、VBAなんて所詮、実行時にアバアバな型チェックしているだけだろっ、っうに。もうSet地獄から逃れたいです… で、なぜかMethodは5つもありますがな。Sub、Function、Property Get、Property Set、Property Let…。SubとFunctionはまぁ、許そう。Propetryっていうのがねぇ、気持ちが悪い。Propertyっていうのがあるためにクラスとして完全なクロージャーが実現していねえんじゃねぇ??と思ってみる… あと、当然のごとく(そろそろしつこいかも…、すんません)、クラスでプロパティを保持するクラス変数はありません。 以上のようなことに当分の間はまっていました。VBAに期待??しすぎなのだろぅか。次は演算子編の予定。 ※猫作業とハムスター作業の違いについて コメント
かなり前の記事にコメントして申し訳ないけど >higeさん 今の職場だとExcel2000のVBAぐらいしか使えないので・・・ VBAで私が泣いたのは
まぁ、妥協の塊のようなメリットですが・・・ オブジェクト志向で困ったといえば、SingleTonなクラスが実現できないとか モジュールもクラスみたいなものなんだから、オブジェクトとして扱わせてくれよ・・・と思ったり・・・ 気持ち悪いコードがたくさん出てきますよ 実行速度でも ここまで書いておいて何ですが VBAで泣かないためには、WindowsAPIを学んだ時のような・・・哀しい覚悟が必要ですね・・・ Posted by: hige : October 10, 2009 02:48 PM>higeさん Setについてですが確かに面倒ですね。 DIM foo as Range こう書かれていて、これをどう解釈するかが、Setなしには立ち行かなくなるのが痛い。デフォルト・プロパティがなければ、(1) では foo に Range("B2") の参照が代入されるとVBA側が解釈すればよいのですが、実際にはデフォルト・プロパティであるvalueがあるために、 foo.value = Range("B2").value という結果と同じになってしまいますよね。Set の有無で解釈が変わってしまう(動作が変わってしまう)のもいただけません。デフォルトがあると便利だろうと考えてそのようにしたのかもしれませんが、おかげで Set を余儀なくされてしまいました。 仕様と言えばそれまでですが、個人的には使用するプロパティは明示されるべきだと思います。 foo.value = Range("B2").value これでいいじゃないかと。デフォルト・プロパティを考えた人は、「ナイス!」って思ったんでしょうね。。。トホホです。 Posted by: ironya : February 18, 2011 11:33 AM>ironyaさん 以下のものはどうですかね Posted by: て : October 17, 2017 09:31 PMコメントする
|
スポンサード リンク
|