Upgrade to Pro — share decks privately, control downloads, hide ads and more …

VBAナメてた

Narazaka
April 27, 2016

 VBAナメてた

〜VBAを使ったら絶対に後悔する7つの理由〜
社内でLTしたスライドです

Narazaka

April 27, 2016
Tweet

More Decks by Narazaka

Other Decks in Programming

Transcript

  1. VBA
    ナメてた
    @narazaka

    View Slide

  2. 奈良阪
    自己紹介
    Twitter:
    Github:
    npm:
    CPAN:
    RubyGems:
    ドリコム2015
    新卒入社 サーバーサイドRuby
    好きな言語: Perl / CoffeeScript / Ruby / C# / Ceylon?
    その他:
    伺か/
    漫画読み描き/OP
    アニメ愛好家/

    @narazaka
    @Narazaka
    @narazaka
    NARAZAKA
    Narazaka

    View Slide

  3. VBA
    (Visual Basic for Applications)
    1994
    年のExcel5.0
    から付属したマクロ用言語
    Excel
    が有名だがWord
    やPowerPoint
    等でも使える

    View Slide

  4. 顧客が説明した要件
    プランナーさん:
    クエスト作成を便利にしてや
    奈良阪: xlsx
    使っとるしVBA
    やと移行コスト低そうか?

    View Slide

  5. プログラマの見積もり
    プランナーさん:
    ウィッスオナシャス
    奈良阪:
    メンテコスト高いらしい
    奈良阪:
    綺麗にかいたらそんなでもないやろ(
    慢心)

    View Slide

  6. VBA
    ナメてました

    View Slide

  7. 「Excel
    マクロつらい」

    View Slide

  8. 謎のセル指定

    View Slide

  9. なるほど……

    View Slide

  10. VBA
    、オブジェクト指向言語らしい?
    クラス書いたらよくね?

    View Slide

  11. 適切な変数名でマシになるっしょ?
    table_area = Range(area_begin, area_end)

    View Slide

  12. ……

    View Slide

  13. クラスにもした
    変数名関数名とかにも気を配った

    View Slide

  14. View Slide

  15. でもそういう問題ではなかった

    View Slide

  16. VBA
    ||
    20
    世紀のMS
    製品

    View Slide

  17. 最近のMicrosoft
    に毒気を抜かれて忘れていた

    View Slide

  18. 生産性が惨殺される体感

    View Slide

  19. 古き良きM$
    を思い出させてくれる糞仕様の数々

    View Slide

  20. 7
    連発

    View Slide

  21. VBA
    を使ったら絶対に後悔
    する7
    つの理由
    (
    煽りタイトル)

    View Slide

  22. 1.
    不完全な型システム

    View Slide

  23. VBA
    は一応オプショナルな変数型指定
    を持ちます

    View Slide

  24. TypeScript
    のように、変数宣言時や関数宣言時にオプショ
    ンで型をつけられる
    これは良い

    View Slide

  25. 型付で宣言された変数はエディタ上でインスペクタが出て
    使えるメソッドとかが出てくる
    これも良い

    View Slide

  26. 型情報最高!!

    View Slide

  27. にもかかわらず

    View Slide

  28. エディタでもコンパイラでも型チェッ
    クされない

    View Slide

  29. ?

    View Slide

  30. 「型が一致しません (
    エラー 13)
    」はランタイムエラー

    View Slide

  31. 引数の順番とか間違えてても全部ランタイムエラー

    View Slide

  32. せっかく入力したのに……
    型情報の持ち腐れ

    View Slide

  33. 不完全な型システムややつ
    らい

    View Slide

  34. dis
    ばかりでは一面的なので他言語などと比較して
    ※許せる点
    エディタ上だけとはいえインスペクタ働くのは良い
    実行時型判定でエラるので早期エラー発見にはなる
    どちらかといえば「口惜しい」
    その他付随したしんどい点
    変数名の補完はしてくれないのでめんどい

    View Slide

  35. 2.
    プリミティブ型とオブジ
    ェクト型で代入の方法が異
    なる

    View Slide

  36. VBA
    は一応オブジェクト指向言語

    View Slide

  37. プリミティブ型とオブジェクト型
    C++
    やJava
    と同じ感じ
    プリミティブ型: Integer, Boolean

    オブジェクト型: Range,
    ユーザ定義等

    View Slide

  38. プリミティブ型とオブジェクト型で代
    入の方法が異なる

    View Slide

  39. ?

    View Slide

  40. プリミティブ型は
    Value = 1

    View Slide

  41. オブジェクト型は
    Set Value = New MyClass

    View Slide

  42. オブジェクト型の場合先頭に
    をつけなければならない

    View Slide

  43. ミス→
    ランタイムエラー
    エディタは検出してくれない
    しかもエラーメッセージが謎

    View Slide

  44. 検出困難
    なれるとそこまで間違わなくなるが、書き始めた初期はヤ
    バかった。

    View Slide

  45. 似たようなつらみ
    関数とサブルーチン
    返値あり ->
    関数 (Function)
    返値なし ->
    サブルーチン (Sub)
    の別もある(Fortran
    にもある)

    View Slide

  46. 呼び出し書式が違う

    View Slide

  47. 関数は引数に括弧をつける
    Set Data = Table.GetData(Row, True)

    View Slide

  48. サブルーチンではつけない
    Table.AddData RowData, True

    View Slide

  49. 関数呼び出しの不整合→

    ンタイムエラー
    エディタはスルー

    View Slide

  50. つらい

    View Slide

  51. プリミティブ型とオブジェクト型で代
    入の方法が異なる
    関数とサブルーチンの呼び出し方法が
    異なる
    つらい

    View Slide

  52. ※許せる点
    C++
    でも値とポインタとの別があるし、(*
    をつける場合が
    有るので)
    代入方法が異なると言えなくもない
    関数とサブルーチンの別はFortran
    にもある(
    サブルーチン
    はcall
    を先頭につけて呼び出す)

    View Slide

  53. 3.
    関数が第一級オブジェク
    トではない

    View Slide

  54. 自分がこれまで使った言語
    JavaScript(ES3,5,2015)
    Perl5.8
    ~5.22
    Fortran95
    C
    C++(03
    、11)
    D
    Java
    Python3
    Ruby(2.0
    以降)
    C#(5.0
    、6.0)
    Excel VBA
    TypeScript
    CoffeeScript
    華和梨8.2.8(kis)
    Windows
    バッチファイル
    bash
    スクリプト

    View Slide

  55. VBA
    、バッチファイル、シェルスクリプトのみ
    関数が第一級オブジェクトとして扱えない

    View Slide

  56. each
    map
    lter
    VBA
    では本質的に 以外で実装が出来ない

    View Slide

  57. For Next
    回すしかない

    View Slide

  58. つらい

    View Slide

  59. 関数が第一級オブジェクトではないの
    あるのに慣れてるので結構辛い

    View Slide

  60. ※許せる……?

    eval
    すれば使える
    DSL
    ではそういうこともある

    View Slide

  61. 4.
    エディタで1
    行ごとに構文
    チェックが走る

    View Slide

  62. (
    厳密には言語の特徴ではないが)
    エディタで1
    行ごとに構文
    チェックが走るのがひどい

    View Slide

  63. Visual Studio
    とかのIDE
    も改行したら行整形したりする
    が……

    View Slide

  64. 関数を書こう

    View Slide

  65. if
    文を書こう

    View Slide

  66. FirstRowIndex
    という定数と比較したい
    変数名補完が効かないし長いからコピーしてこよう

    View Slide

  67. カーソルを別の行へ

    View Slide

  68. !?

    View Slide

  69. 行ごとに文完結してないとエラーがダイアログで出る
    いちいちOK
    押さないと別の編集ができない
    ついでにまともな修正候補は出ない

    View Slide

  70. とりあえず意味のない値で文完結させて別の行へ

    View Slide

  71. ……

    View Slide

  72. きっとこれを面倒がって短いA
    とかB
    とかの変数名が書かれ
    るんだろうと思うと……

    View Slide

  73. エディタで1
    行ごとに構文チェックが
    走ってしかもいちいちダイアログが出

    つらい

    View Slide

  74. ※許せる?

    不十分すぎるが文法エラー出してくれるのは良い

    View Slide

  75. 5.
    ソースがxlsx
    バイナリの中
    に保存される

    View Slide

  76. つまり自然にバージョン管理や差分比較することが出来な

    View Slide

  77. ※許せる点
    xlsx
    がメインでその付属スクリプトという性格からしょ
    うがない面がある
    比較的許せる

    View Slide

  78. ソースがxlsx
    バイナリの中に保存され
    るのつらいけど許せる

    View Slide

  79. 6.
    継承ができない

    View Slide

  80. 「VBA
    は一応オブジェクト
    指向言語」

    View Slide

  81. クラスの継承が出来ない

    View Slide

  82. 運用で回避あるある
    クラスにアクセス制御がなかったりするLL
    命名規則とかでなんとかする

    View Slide

  83. 回避できない
    VBA
    はアクセス制御があるのに継承がない
    委譲しよう→関数が第一級ではないのでつらそう

    View Slide

  84. インターフェースは継承をすることは
    可能
    ' Class1
    Implements Class2
    Dim Obj1 As Class1
    Set Obj1 = new Class1
    Call Obj1.class2method ' Dim Obj1 As Class1
    Set Obj1 = new Class1
    Dim Obj2 As Class2
    Set Obj2 = Obj1 ' !?
    Call Obj2.class2method

    View Slide

  85. つらい

    View Slide

  86. 他OOP
    系のつらみ
    コンストラクタに引数が渡
    せない

    View Slide

  87. Set Obj = New MyClass(hoge) '

    View Slide

  88. Set Obj = New MyClass
    Obj.Setup(hoge)

    View Slide

  89. つらい

    View Slide

  90. 継承ができない
    コンストラクタに引数が渡
    せない
    ごっつつらい

    View Slide

  91. ※許せる点
    一応クラスは作れる

    View Slide

  92. 7.
    スタックトレースが存在
    しない
    呼び出し元しかわからない

    View Slide

  93. エラーにスタックトレースがつかない
    エラーが起こった処理の呼び出し元しかわからない

    View Slide

  94. 最高にヤバい

    View Slide

  95. 大抵の言語ではエラー時「スタックト
    レース」が出る

    View Slide

  96. View Slide

  97. スタックトレースのない言語はシェルスクリプト等他に
    も存在する
    しかしそれらは最低限実際にエラーになったソース行が
    わかる。

    View Slide

  98. in VBA

    View Slide

  99. エラー発生!

    View Slide

  100. 情報1:
    エラー内容とエラーコード
    (
    この時点では行がわからない)

    View Slide

  101. 情報2:
    呼び出し元の行情報

    View Slide

  102. 以上

    View Slide

  103. エラー時に分かる情報
    情報1:
    エラー内容とエラーコード
    (
    型が一致しません (
    エラー 13))
    くらいの超簡易な情報
    情報2:
    呼び出し元の行情報

    View Slide

  104. エラー内容詳細を見たい
    ヘルプを押しても

    View Slide

  105. View Slide

  106. 検索しても

    View Slide

  107. ググるしかない

    View Slide

  108. エラーのたびに……
    1.
    エラー内容とエラーコード
    2.
    呼び出し元の行情報
    しか提供されないので
    エラー内容詳細
    ググる
    エラーの起きた場所
    呼び出し元からブレークポイントをふりつつ関数を1
    つずつ
    自分でたどって行を絞り込んでいく

    View Slide

  109. 苦行

    View Slide

  110. スタックトレースが存在し
    ない
    呼び出し元しかわからない

    View Slide

  111. ※許せない

    View Slide

  112. 7
    つの大罪
    1.
    不完全な型システム
    2.
    プリミティブ型とオブジェクト型で代入の方法が異なる
    3.
    関数が第一級オブジェクトではない
    4.
    エディタで1
    行ごとに構文チェックが走る
    5.
    ソースがxlsx
    バイナリの中に保存される
    6.
    継承ができない
    7.
    スタックトレース不在 呼び出し元しかわからない

    View Slide

  113. 7
    つの知見
    1.
    合理的な型システム
    2.
    代入や呼び出しの方法が一貫している
    3.
    第一級関数
    4.
    柔軟なIDE
    5.
    テキストでソースが保存できる
    6.
    継承ができる
    7.
    スタックトレースがある
    素晴らしい

    View Slide

  114. 当たり前に感謝

    View Slide

  115. 教訓

    View Slide

  116. 次はVBA
    以外で
    やる

    View Slide