「達人プログラマー」を読んでみた。
📖

「達人プログラマー」を読んでみた。

Category
Author
Tags
Description
この本はプログラマーであるけれど、これ以上先に進むにはどうすれば良いか、よく詰まること、陳腐化することってあるよね、そういうときにどうすればよいかを記した本です。
Published
September 27, 2022
Last Updated
Last Updated October 28, 2022
Writings
この記事は約7分で読めます
今回読んだ本
達人プログラマー ―熟達に向けたあなたの旅― 第2版
より良いプログラマになるための実践的アプローチ本書は、David Thomas and Andrew Hunt, The Pragmatic Programmer 20th Anniversary Edition (Addison Wesley, 2019)の日本語版です。本書は、より効率的、そしてより生産的なプログラマーになりたいと願うソフトウェア開発者に向けて、アジャイルソフトウェア開発手法の先駆者として知られる二人により執筆されました。経験を積み、生産性を高め、ソフトウェア開発の全体をより良く理解するための、実践的なアプローチが解説されています。先見性と普遍性に富んだ本書は、入門者には手引きとなり、ベテランでも読み直すたびに得るものがある、座右の一冊です。 序文目次まえがき-第2版に向けて第1版のまえがきより 第1章 達人の哲学1 あなたの人生2 猫がソースコードを食べちゃった3 ソフトウェアのエントロピー4 石のスープとゆでガエル5 十分によいソフトウェア6 あなたの知識ポートフォリオ7 伝達しよう! 第2章 達人のアプローチ8 よい設計の本質9 DRY 原則| 二重化の過ち10 直交性11 可逆性12 曳光弾13 プロトタイプとポストイット14 専用の言語15 見積もり 第3章 基本的なツール16 プレインテキストの威力17 貝殻(シェル)遊び18 パワーエディット19 バージョン管理20 デバッグ21 テキスト操作言語22 エンジニアリング日誌 第4章 妄想の達人23 契約による設計(DbC)24 死んだプログラムは嘘をつかない25 表明を用いたプログラミング26 リソースのバランス方法27 ヘッドライトを追い越そうとしない 第5章 柳に雪折れ無し28 分離29 実世界を扱う30 変換のプログラミング31 インヘリタンス(相続)税32 設定 第6章 並行性33 時間的な結合を破壊する34 共有状態は間違った状態35 アクターとプロセス36 ホワイトボード 第7章 コーディング段階37 爬虫類脳からの声に耳を傾ける38 偶発的プログラミング39 アルゴリズムのスピード40 リファクタリング41 コードのためのテスト42 プロパティーベースのテスティング43 実世界の外敵から身を守る44 ものの名前 第8章 プロジェクトを始める前に45 要求の落とし穴46 不可能なパズルを解決する47 共に働く48 アジリティーの本質 第9章 達人のプロジェクト49 達人のチーム50 ココナツでは解決できない51 達人のスターターキット52 ユーザーを喜ばせる53 自負と偏見 後書き参考文献演習問題の回答(例)索引Tip一覧著者について
達人プログラマー ―熟達に向けたあなたの旅― 第2版
達人プログラマー新装版

本の印象

この本はプログラマーであるけれど、これ以上先に進むにはどうすれば良いか、よく詰まること、陳腐化することってあるよね、そういうときにどうすればよいかを記した本です。
 
例えば割れ窓理論という話があります。家の窓が割れていたらどうしますか?当たり前ですが修理しますよね。逆に修理を放置したらどうなるでしょうか。誰も何もしなければそれは不良学校のような荒れた場所になります。
これはソースコードでも一緒です。100人規模で開発してると汚いところはわかっているけれど、放置するなんてことはザラにあります。段々と荒れ果てた地になっていくので、なるべく早く窓を修理してしまいましょう。
割れた窓
割れた窓
 
以下、気になったところをどんどん書いていきます。

ソフトウェアの哲学編

十分に良いソフトウェア

ソフトウェアには不良は必ずある。が、そこまで神経質になる必要はなく、90%のユーザが満足すればそれでよい。残りの10%を追い求めようとすると生産性は下がる。

知識ポートフォリオ

IT分野の進化のスピードは凄まじい。今ある技術もいつか陳腐化することを前提でいること。バナナや野球のチケットのようなもの。
ポートフォリオの管理ポイント
  1. 定期的な投資
  1. 分散投資
  1. 堅実な投資とハイリスク投資のバランス
  1. 定期的に見直して再分配を行う
💡
知識ポートフォリオは金融ポートフォリオと似ている

設計のアプローチ編

良い設計の本質

良い設計とは悪い設計よりも変更しやすい。ETC原則(EasyToChange)
  • 結合を単一化する
  • 名前の付け方を深考する
良い設計をするための習慣
💡
設計時の状況を日誌に残し、選択肢と変更時の前提を残し振り返りを行う

DRY原則は基本的に守る、時には破る

ログ表示などlowレベルなレイヤーは二重化されるべきで、highレベルなコントローラーレイヤーは二重化するべきではない。validate処理などは似ているように見えて要求仕様が一緒であるだけ。変化する可能性がある。

直交性

コンピューティング分野では独立していない、結合度の低い場合直交しているといえる。
notion image

直交していることの利点

依存度の高いシステムの場合、局所的な修正では済まない。
関係のないコンポーネントの影響を受けない
生産性の向上
  • 変更の局所化で開発期間とテスト工数が短縮
  • 新機能は新しいコードの追加となり既存コードの変更が不要
  • A機能、B機能が直行していれば AxBの機能が実現できるが、直交していなければ(依存してれば)機能重複するのでAxBよりも必然的に少なくなる
リスクの低減
  • 障害時、改修時影響範囲が小さい
  • 検証が容易い

コーディング

  • コードの結合度を最小化する
    • デメテルの法則
  • グローバル変数を避ける
    • Singletonパターン(1つのクラスインスタンスのみ制限するパターンだが、多くの人はグローバル変数的な使い方をするので注意)
  • 類似機能を避ける
    • 共通コードが最初と最後にあるなどよくある話
    • コードの二重化を避けるデザインパターンとしてStrategyパターンを参考にする

可逆性

エンジニアは与えられた課題に対して、簡潔なたった一つの解決策を好む。
何かを実装する場合解決策は複数個あり、ベンダーやビジネス状況により3個にも5個にもなり得る。変更されないシステムなどない。
例えばAデータベースを開発を進めているとして、開発終盤に明らかにBデータベースよりも遅いことがわかってしまった場合、データベース永続化部分だけ抽象化できていれば、いつでも交換できる、可逆性のあるシステムだと言える。
Webアプリではなくてモバイルアプリが欲しいとビジネス側に要求されたら?APIだけ切り出せていればそこまで手戻りは少なくなるはずである。

プロトタイピングで勘違いすること

プロトタイピングはあくまで使い捨てのプロダクトということが関係者全員が理解できていないとプロジェクトが進んだときに勘違いする。
そのプロトタイピングに魅せられたマネージャーが「これで行こう!」と勘違いしてしまうことが往々にしてあり、あくまで使い捨てなので工数は別でかかることを共通認識でいる必要がある。

内部ドメイン言語と外部ドメイン言語

内部

言語特有の記述方法であったり、Ruby RSpecなどの書き方など

外部

AnsibleやOpenAPIなど JSON, YAML, CSVなどで構成できる言語のこと。
一般的にこれらの言語の方が可逆性は高いと言える。

見積り

見積もりの伝え方。15日の場合は15日かかると伝える。10週かかる場合は 3ヶ月と伝える
  • 1~15日 ⇒ 日
  • 3~8週 ⇒ 週
  • 8~20週 ⇒ 月
  • 20週超え ⇒ 大きすぎるので提出する前に再考するか、分割する

見積りはどこから来るのか

  • 一番の秘訣は過去に似たようなことをした人にどのくらいかかるか聞く
    • それがMaxである
  • 過去のチケットと比べる

PERT手法(Program Evaluation and Review Technique)

  • タスクに対して楽観時間、最確時間、最悪時間を算出する

見積り精度をあげるには

見積もり精度の振り返りを行い、どのくらい誤りがあったか毎回測定をする
何回も繰り返して精度を上げていくこと。似たような案件は必ずあるため、事例の調査をする。

エンジニアツール編

エディター

vimを使いこなそう!!(本著には記載されていません。。。w個人の見解です。)
毎日1時間かかる作業を10%効率を上げると月で5時間も浮くことになる。

まずはチャレンジ

  • オートリピートを使わずにブロック選択して削除
  • マウス、トラックパッドを使わない生活を1週間行う
  • 統合できる場所を探す
  • Pluginを探す、もしくは自作する

デバッグ時の思考法

  • バグが起きたときのスタックトレースを2分探索法で行うことを癖付ける
    • 上から順になめると O (N), 2分探索であれば O(log n)となる
    • ログを真ん中あたりでまずは見る、上下でバグがあるレイヤーを探し更に2分探索して見つけ出す
    • リリース時の障害探索でも同じ方法が使える

ラバーダッキング

まずは人に話すと話すために思考整理するため、勝手に問題解決につながる

思考実験

  • PCにコーヒーをぶちまけたとする
  • 会社に新しいパソコンの申請をし、新しいパソコンがくる
  • PCのセットアップ、元の状態に戻すまでどのくらいかかるか、嫌な顔をされるかを想像する

リソースのバランス方法

どんな言語でもメモリーの開放を意識してプログラミングしたほうが良い。
CやC++はなおのこと、Javaなどのガーベッジコレクションで管理されてるものであれば、GCの動きを意識したほうが良い。
Javaでよくオブジェクト使用後にNullを設定することがあるが、それはGCにリソース開放を長い目で見たときに効率より早くしてもらうためである

ヘッドライトの先を越さない

車のヘッドライトの照射距離は約50m、対して時速60kmでの停止距離は58m、時速110kmだと140mだそう。ヘッドライトの先を越すことはそんなに難しくない。
つまり小さく進んだほうが停止距離内なので安全である

柳に雪折れなし

コードに柳のような柔らかさ、柔軟性をもたせれば雪(外部要因)で折れることはない
  • Observerパターン
  • PubSubパターン
  • リアクティブプログラミング(RxJS, webflux)
  • 継承は悪。インタフェースはOK
  • 継承が答えになることは滅多にない
  • 外部設定でアプリケーションをコントロールする
  • Config as a Service
    • 設定を外部に切り出しアプリケーション事に変更、変更時に通知できるようにすれば柔軟性のある設計になる

コーディング段階

テストはバグを発見するものではない。設計、APIや結合の観点を得るためである。
テストの利点はテストについて考えテストを作り出してる時に生み出される(テストファースト)
地雷原を渡るような偶発的プログラミングはやめよう。

リファクタリング

リファクタリングと機能追加を同時に行ってはいけない
リファクタリング前にテストを用意すること。何回も実行すること
名前の変更はかなり難しい。名前はすぐに誤解を呼ぶ名前をつけてしまう。
例えば getData というメソッドからデータを保存する処理も同時にしていたなどあり得る話です。

プロジェクトを始める前に

相談者はプログラムを読めるわけではない。要件定義書はBiz側とDev側の差を埋めるものであり、より詳細な仕様を書いても意味がない。

協働する

ペアプログラミング、モブプログラミングは会議よりも良い方法です。コードを書く中で議論をしてより良いコードを書く方法です。

読んだ感想

感想
意外と書いてあることは人間的なコミュニケーションが主体でした。ソフトウェアは人が作るものなので人を知ることも重要であるというのがわかりました。 プログラマーとして生きていくのにポートフォリオの話などまさに参考になったと思います。毎年1言語覚えるのが理想であると書いてあり、まさにだなぁと感じました。

読むべき対象者

  • ある程度実務経験をしているプログラマー
    • 話の内容が抽象的な部分が多いため、経験をしていないと具体的に想像できないことがある
  • プログラム言語を学ぶというより、プログラムの哲学を学ぶための書なので、具体的な解決策を望んでいる場合にはおすすめできない
  • 今やってる方法でよいのかどうか確認や実務経験でやったことを体系的に思い出す際に読むと良いです。
 
今回読んだ本
達人プログラマー ―熟達に向けたあなたの旅― 第2版
より良いプログラマになるための実践的アプローチ本書は、David Thomas and Andrew Hunt, The Pragmatic Programmer 20th Anniversary Edition (Addison Wesley, 2019)の日本語版です。本書は、より効率的、そしてより生産的なプログラマーになりたいと願うソフトウェア開発者に向けて、アジャイルソフトウェア開発手法の先駆者として知られる二人により執筆されました。経験を積み、生産性を高め、ソフトウェア開発の全体をより良く理解するための、実践的なアプローチが解説されています。先見性と普遍性に富んだ本書は、入門者には手引きとなり、ベテランでも読み直すたびに得るものがある、座右の一冊です。 序文目次まえがき-第2版に向けて第1版のまえがきより 第1章 達人の哲学1 あなたの人生2 猫がソースコードを食べちゃった3 ソフトウェアのエントロピー4 石のスープとゆでガエル5 十分によいソフトウェア6 あなたの知識ポートフォリオ7 伝達しよう! 第2章 達人のアプローチ8 よい設計の本質9 DRY 原則| 二重化の過ち10 直交性11 可逆性12 曳光弾13 プロトタイプとポストイット14 専用の言語15 見積もり 第3章 基本的なツール16 プレインテキストの威力17 貝殻(シェル)遊び18 パワーエディット19 バージョン管理20 デバッグ21 テキスト操作言語22 エンジニアリング日誌 第4章 妄想の達人23 契約による設計(DbC)24 死んだプログラムは嘘をつかない25 表明を用いたプログラミング26 リソースのバランス方法27 ヘッドライトを追い越そうとしない 第5章 柳に雪折れ無し28 分離29 実世界を扱う30 変換のプログラミング31 インヘリタンス(相続)税32 設定 第6章 並行性33 時間的な結合を破壊する34 共有状態は間違った状態35 アクターとプロセス36 ホワイトボード 第7章 コーディング段階37 爬虫類脳からの声に耳を傾ける38 偶発的プログラミング39 アルゴリズムのスピード40 リファクタリング41 コードのためのテスト42 プロパティーベースのテスティング43 実世界の外敵から身を守る44 ものの名前 第8章 プロジェクトを始める前に45 要求の落とし穴46 不可能なパズルを解決する47 共に働く48 アジリティーの本質 第9章 達人のプロジェクト49 達人のチーム50 ココナツでは解決できない51 達人のスターターキット52 ユーザーを喜ばせる53 自負と偏見 後書き参考文献演習問題の回答(例)索引Tip一覧著者について
達人プログラマー ―熟達に向けたあなたの旅― 第2版
もう少しレベルが高いのを期待する場合はこちらの新装版をおすすめ