あなたは写経しますか

@katzchangさんの次となるTDD Advent Calendar jp: 2011の11日目記事になります。
登録者一覧を眺めるたびに「他に学生がいない…」と嘆きつつ、ハードルが上がり続けたタイミングでの担当回というこで胃に穴があきそうです。


11月時点では「TDDBCについて書こう」と思っていたのですが、12/1の素晴らしい記事によって書くことがなくなったり*1、日々追加されていく素敵記事を眺めながらどんな内容にするか悩んだ結果、釣り気味なものになってしまいました…

はじめに

とりあえず、この10日間に書かれたTDD Advent Calendar記事を振り返ってみましょう。まだ読んでない方は、まずは10日目までの読んでみてください。
まず、TDD少年の想い学ぶべき理由を知ることができます。そしてTDDを学ぶ前に身に付けておくといいと思う基礎体力が提示され、TDD入門方法の1つが紹介されています。また、TDDを学ぶことで得た知識はこのような現場でも役にたつことが示されています。
TDD練習フェーズでは、例えばPerlでの環境構築方法Javaでの実演風景Javaのサンプルを見てTDDのリズムを知ることができます。また、TDDする際の手助けとしてのカバレッジに対する考え方や自分を取り巻く対象をプログラミング対象(そしてTDD練習の対象)にできることが読み取れます。
TDDを練習していくうちに仲間がほしくなったり広めたくなったらTDDBCを開催してみるのも一つの方法です。


さて、振り返りながら私に何が書けるのかを考えてみたのですが、私が書けることはTDD入門に関することかなということで、@goyokiさんとネタ被りではありますが書いていこうと思います。

あなたは、写経しますか?

多くの方が少なくとも一度以上の写経経験があると思います。
では、動画で出てきたコードを書きとったり、GitHubなどで公開されているコードをログにしたがってトレース*2したことがありますか?こちらは見た、または読んだけど書くまでは…という感じでしょうか。
Web+DB Press連動の和田さんの動画にこんなことが書かれています。

写経では得られない典型的なものの一つが、「リズム」なんですね。実際に本を手で写してみても、ではKent Beckはどういう感覚でテストを起動していたのか、私はどういう感覚でテストを起動していたのかということは、伝わりません。

動画で解説 和田卓人のテスト駆動開発講座 第7回

コードの流れを本に書くことはできても、リズムは書けません。TDDBCの参加理由として「TDDのリズムを知りたい」があるのは、こういった背景も関係しているのだと思います。
リズムを知りたい、身につけたいという方にまずお勧めするのはTDDBCです。TDDBCでは実際に自分の手を動かしますし、経験者から助言もいただけたりします。また、そこそこの確率で自分の希望した言語でのTDDリズムを知ることができます。しかし残念なことに、抽選に漏れた、どの開催地も遠くて参加できない、予定があわずになかなか参加できない…など、様々な理由でTDDBCに参加できない可能性があります。
TDDBCに参加できない場合でも、動画を見て学ぶことができます。TDDBCが頻繁に開催されるようになるまでは、おそらくこれが主流だったのではないでしょうか。動画は開発者の開発スタイルをほぼそのまま視覚情報として視聴者に与えてくれます。これは、セミナーなどで行われているデモにも同じことが言えます。
もう一つ方法があり、GitHubやBitbucketで公開されているTDDBC演習成果をトレース、分析する方法です。歴史改変を行っていないコミットログを見れば、コミット時刻からTDDリズム、コミットメッセージやソースコードから何を実装したかがわかるので、やり方を考えればTDDのリズム*3を知り、身につけることも可能です。ただし、どんな操作を行ったなどの情報がないのと、あくまで時刻というデータ情報なので、リズムを身につけるための道具として使うためには一工夫必要になります。逆にメリットは、お題が入門としてちょうど良い大きさであること、自分が使える言語のデータが公開されている可能性があることです。私が検索した範囲ではGitHubとBitbucketにてJava/C++/Ruby/PHP/C#/Python/Groovy/Scala/OCaml(?)/JavaScript/F#のリポジトリを発見できました。
写経、動画を視聴、ログ解析やコードのトレースは誰でも一人できます。つまりTDDは、学ぶのが難しいと言われてはいるものの、一人で学べるスキルなのです。特に現在は様々な情報やデータが出回っているので、一昔前に比べれば格段に学びやすい環境になっていると思います。

TDDBC演習成果からTDDプロセスを学ぶ

さてここからは、誰得感強めですがTDDBC演習成果からTDDプロセスを学ぶ方法について書きます。
内容は以下のような順序になります。

  1. まずはそのまま書き写す
  2. わからなかったことを理解できるようになるまで調べる
  3. お題の仕様とテストリスト(TODOリスト)を線で結ぶ
    • テストリスト(TODOリスト)が公開されている場合
    • テストリスト(TODOリスト)が公開されていない場合
  4. 時間をはかる
  5. 道具を磨く
  6. (議論を写経する)

基本的には私が研究でデータ解析するときにやったりすることを組み合わせたもので、全部やろうとするとそこそこ時間が必要になります。
メリットとしては

  • 言語ごとのTDDプロセスが学べる
  • 自分に足りない知識を補強できる
  • ツールを使う練習になる
  • 場合によっては、TDDしないほうがやりやすい部分を知ることができる

デメリットはとにかく時間がかかることです。

まずはそのまま書き写す

コミットされた順序でコードを書き写していきます。その際、わからなかいことを見つけたら、わからなかったことをメモしてリストアップしていきます。ブログなどで解説が書かれているデータの場合は解説の順序に従って写していきましょう。また、バージョン管理もしておいてください。
ここでの目的は、どの順序でテストケースを選択しているか、どのタイミングでリファクタリングしているかなどの開発の流れを知ることです。

わからなかったことを理解できるようになるまで調べる

前ステップでわからなかったことをリスト化したので、リストからわからないことがなくなるまで時間の許す限り調べていきます。調べたこともバージョン管理しましょう。
わからないことをわからないまま次に進むのは後々負債になりかねないので、ここで清算しておきます。

お題の仕様とテストリスト(TODOリスト)を線で結ぶ

これは開発者がブログなどでテストリストなどを公開している場合とそうでない場合で少しやることが異なります。
テストリストやTODOリストが公開されている場合は、仕様とリストを眺めながら関連しそうなものを線で結んだり、解説が書かれている場合などは更に、流れを想像しながら疑問に思ったことや状況、要求などを書き込みつなぎあわせていきます。たとえばbleis-tiftさんのTDDBC東京1.6のデータを基にやってみると、最初のほうは以下のようになりました。

ここでは3,4色程度のボールペンを、目的にあわせて色を変えながら使っています。とにかく情報や疑問に思ったことを書き込んでいきます。
テストリストなどがない場合は、テストケースや期待値などからリストを作成し、書き込んでいきます。
注意点としては、あくまでこの作業は自分の想像で書いているということです。開発者は同じ考えだったかもしれませんし、全く違う考えでリストを作成したかもしれません。真相は聞いてみるまでわからないので、気になった場合は質問してみるといいかもしれません。
このステップでの目的は、仕様をどうやって細切れにしていくのかを知ったり、自分で試しに細切れにしたりすることです。

時間をはかる

さて、そろそろコードを書きたい欲求がでてきていると思うので、再びコードを書き写す作業に戻ります。ただし、最初に行った"とりあえず書き写す"わけではありません。作業は下記の順序で行っていきます。

  1. コミットログのコミット時刻からコミット間隔を導出する(間隔が10分を超えるものは10分にする)
  2. タイマーを用意する(好みのものがなければツールを自作しましょう)
  3. タイマーにコミット間隔を入力しスタートさせ、コードを書き写しはじめる
  4. タイマーがなるまでに書き写し終わらなかったコミット部分があったら、間に合わなかったことを記録して書き写しを続ける

このフェーズでは、記録されているデータのTDDプロセスと自分の書き写す速度を試しに比較します。TDDプロセスは早く回せればいいというわけではないですが、設計判断をしながら実装しているデータよりも明らかに書き写す速度が遅い場合は、自分が使っている道具をうまく扱えていない可能性があります。次のフェーズで訓練しましょう。
ここでの目的は速さを競うことではありません。あくまで道具をきちんと扱えているかの確認と、他開発者のTDDのリズムを知ることが目的となります。

道具を磨く

データよりも書き写す作業が遅かったと言うことは、つまりエディタやIDEといった道具を使いこなせていないことを意味します。道具を磨き、腕を磨くことでスムーズにコーディングできるようになりましょう。たとえばIDEのショートカットコマンドを覚えたり、エディタをカスタマイズしてより開発しやすい環境にしていくのです。
エディタの設定やプラグインに何を使えば効率がいいのかでわからないことがあれば、他の人に相談してみましょう。その人は何か良い方法、ものを知っているかもしれません。
道具を、腕を磨くことで開発効率があがります。そしてそれはTDDにも良い影響を与えるので、ここで訓練して改善していきましょう。


さて、一つのリポジトリに対して行う作業の流れは以上になります。
最初はなれないのでかなり時間がかかると思われますが、数をこなしていくうちにかなりTDDに慣れるので、慣れてきたらこの方法から離れ自分のスタイルでTDDすればいいと思います。

(議論を写経する)

TDDはできるようになりました。ですが、TDDを習得できたとして誰かに利点や欠点をきちんと説明できるでしょうか?
できないと思った場合は資料をどんどん読み返しましょう。さらに、時間があれば講演などを写経してみましょう。かなり時間のかかる作業ではありますが、写経するために一字一句逃さず聞くことになるのでとても勉強になります。
このステップはオプション項目です。自分の言葉ですでに説明できる人はこんなことしなくてもいいですし、講演の写経などはとにかく時間を使うので時間がないのであればやらないほうが無難です。

おわりに

長くなってしまいましたが、結局何が言いたかったのかといえば、TDDは一人でも学べるよということ、せっかくTDDBCの演習成果が公開されているので分析しながら自分のTDD力上昇に役立ててみてはいかがでしょうか、ということでした。


次は@irofさんのテストと言うパートナーです。

*1:TDD Advent Calendarはネタ被りOKとなっているのですが、あの記事を見た後では書ける気がしなくなりました

*2:"すでにある物をなぞる"という意味でのトレースです

*3:この場合のTDDリズムは、正確には"DVCS操作を含めたTDDリズム"です