新人プログラマ・エンジニアに培って欲しい3つのこと


## はじめに
新人プログラマ応援、ということで初めて記事投稿してみてます。

#### 自己紹介
まずは自己紹介、ということで遍歴から。

心理学の大学院の時から、WEBアシスタントエンジニアをやって、そこからゲーム会社に就職し、ゲームプログラマー（主にスマホ）を丸6年くらいやり、今は転職してWEB系サービス提供の会社で主にサーバサイドエンジニアやってます。
好きな言語はC++とkotlin,C#で、他に触ったことのある言語はPHP,typescript,Lua,Objective-C,Javaあたりです。

#### 何を書くのか
上に書いたようなこれまでの経験と、何回か新卒エンジニアのメンターやってみた経験も踏まえて、新人プログラマ・エンジニアに培って欲しい技術3つについて書きます。
具体的には下記3つについてになります。

- コードリーディング
- 知識・技術取得フロー
- 手抜きのスキル

## 本題

### コードリーディング
端的に言うと読んで字のごとく「コードを読む力・能力」のことです。
一番目にこれを持ってきたのはもちろん、これが一番大事かな。。。と思っているためで、順々に理由を書いていこうと思います。

##### どういう能力か？
具体的には下記から構成されると考えています。

a.コードそのものを読む能力（速さ、正確さ）
b.コードを読んで理解する能力（コードの読解力）
c.コードの間違い・誤りを見つける能力（コードの識別力）

##### なぜ必要か？
多くの場合は既存プロダクトの保守・改善、リファクタリングをするケースが殆どになってくるため、当然、業務として先達の書いたコードを読まざるを得ない機会というのはたくさんあります。そして、新規開発であっても、ライブラリだったり、ネット上に転がっているコードだったりも読む必要があったりしますし、実のところ「コードを書く」よりも「コードを読む」時間の方が業務の大半を占めるなんてのはざらにあるでしょう。

そしてコードリーディングの能力の先にあるのはデバッグ力（＝コードリーディングしてて間違いに気づく力）であり、レビュー力（＝コードを読んだ上で構造的な誤りや、分かりにくさを見抜く力）であるため、コードリーディングの力を養うことでそういった部分も底上げされてくると思っています。

もちろん、いいコードを読んでそれが蓄積されていけば、いいコードを書く力の素地の一部にも繋がるはずです。
（もちろん、いいコードを書く練習は必要ですが）

##### どうやって培うのか？
いわゆる「（英語とかの）言語の勉強」と同じで、いろんなコードを読むしかないと思ってます。
少なくとも自分にはあまり近道は思いつかないですが「ちゃんと設計された長大なコード」を一通り読みきる、ということを一回するだけでも読み方は変わってくるかもしれません。

I/Fがあると手がかりになりやすいので、例えばSpring-bootあたりはリファレンスと突き合わせて読めば読みやすいでしょう。
・spring-projects/spring-boot
https://github.com/spring-projects/spring-boot

あとは、「色々なプログラミング言語」のコードも読んでいくといいと思います。
きれいなコード、汚いコード、暗黒呪文のようなコード。。。言語によって色々な書き方ができたりしますし、色々な書き方をする人がいるので、読む語彙みたいなものが養われるように思えます。複数言語を読んでみることのもう一つのメリットとして、新しい言語に入りやすくなっていくとも思えるので、それはエンジニアとして一つの強みにもなっていくでしょう。


### 知識・技術取得フロー
新しい言語、新しいフレームワーク、新しいシステム。。。エンジニアをやっているとこういうものを習得しなければいけない場面によく出くわしますが、そういう時に「自分はこうやっていけば間違いない」みたいなフローを構築する、ということです

##### 例えばどういうものか？
人によって千差万別だと思うのですが、私の場合、自分にとって新しい言語を触るときなどは、

1. 既存のコードをざっと読む
1. 自分でカスタマイズして動きを確認してみる
1. 自分で処理を一個書いてみる
1. 特徴的な言語のルールを調べる、言語リファレンスを読む

という感じで「とりあえず触ってみてから知識を入れてく」パターンで取得してます。
理由としては「触ってみないと頭に入らん」というのが大きいため、これが自分の取得フローとなっているわけです。

##### なぜ必要か？
上述した以外だと「まず言語リファレンスを読んでからじゃないと気持ち悪くて書けない」みたいな人もいるでしょうし、「一旦書いてみてコンパイラ指摘をつぶすことで知識を入れていく」という人もいるでしょう。

いずれにせよ、自分なりのフローがある、ということは「新しいものを取得するときの見積もりが立てらる」ことにもなります。見積もりの精度というのはエンジニアにとって永遠の課題だと思っていますが、中でも「新しいもの」に取り組むときの精度こそ高い方がいいと思っていますし、その時にフローが確立されていればある程度見積もりが立ちやすいからこそ必要になってきます。

特に新人として入ってきた場合「既存コード＝新しいもの」となることも多いと思うので、こういった能力を培っておけば、配属後や転属後、さらには転職後でも自分の力を十二分に発揮できるまでの期間を見積もれることにもなってくると思うのです。

##### どうやって培うのか？
周りの先輩にやり方を聞いてしっくりきそうなものをやってみる、自分なりに考えてやってみる。。。等で色々な方法を試してみるのが一ついいですし、プログラミングに限らずこれまでの人生で「やりやすい勉強法」みたいなものを適用してみるのもありかと思います。

大事なのは、やり方が出来てきた時に「どれくらいの期間で」できるようになっているかを振り返ることなので、そこはお忘れなく。。。


### 手抜きのスキル
（仕事の質自体には手を抜かず）いかに手間をかけないで最上の結果を得るか？という意味での「手抜き」です。
もっと言えば、無駄な労力をいかに省くか？ということ。

##### どういう能力か？
過去見てきた具体的な例でいえば、

- 同コードを何回もコピペして同じパッケージ内に重複コードを生成してしまう
- CIを使わずに頑張って手動ビルドをし続ける
- 複数のバッチを作って、1つめが終わるまで監視し、終わり次第手動で2つめを回す

というのがありますが、これをある程度の労力で、

- 必要な処理を共通メソッド化
- CIを導入し、pushごとにビルドされるようにパイプライン構築
- 親バッチを作り、エラーが検知されない限り連続で回す

という風にするということです。
もっといえば「自動化できるところを自動化する」「共通化する」能力と自分の中ではイコールと思っています。あるいは「そうする必要性をちゃんとチームメンバー/上長に理解させ、チーム全体の効率化を進める」能力ともいえそうです。

##### なぜ必要なのか？
極端に言えば自動化できるところを自動化しないのは**不毛**なので、それ以上も以下もないかもしれません。
どうしてもシステム構成的に無理とか、センシティブなデータなのである程度監視しつつでないと難しい、みたいなパターンとかやむに已まれぬ理由もあるものの、本当に無理なパターンは実はないです。
提言した時に「学習コスト・運用/維持コストのほうが高いでしょ」と言われたことありますが、次のプロジェクトとかまで考えると今の段階から入れておけば、次にも活かせるのでそこらへんのコストは相殺されてくるはず（と今は思ってます）。

エンジニアとして解決すべき課題、実装（実現）すべき内容から離れたものは、やはりできる限り最初に手間をかけて、あとは手間なしで運用すべきだと思いますし、そうすることで自分たちがやりたいことに取り組む時間は増えていくはずです。
なので、いかに無駄なところを手抜きできるかは肝要ということになってきます

##### どうやって培うのか？
基本的に慣例的に「やり続けている」みたいなものを怪しんだり、自動化方面の知識を持っておく必要があります。

それだけで自動化そのもは実現できるでしょうがサラリーマンとしては、「いかに現状がデメリットが多く、自動化することでメリットがあるか」を説明できるとベストでしょう。
つまり、「いまのデメリットを分かりやすく抽出し、自動化によってどれだけ低減できるか？」をコミュニケーションで伝える必要があります。そこらへんは会社の方針等にもかかってくるので、会社になれること、普段からコミュニケーションを取ってメンバーや上長の人となりを知っておくこと。。。で「人を巻き込む力」を鍛えていけば、いいと思います

そして、何より自分が「あ、これ面倒くさいな。自動化できるんじゃね？」という感覚を鋭く磨いておくのが一番大事かもしれません。


### まとめ
そんなわけで、自分事を振り返りつつ、長々と書いてみました。

「新人プログラマ応援」という枠で色々な方が書いているのを読んだりしても、やはりエンジニアは十人十色だなあ、と思うので、私自身の書いたものも「イチエンジニアがこんなこと言ってるんだな」程度に思ってもらえると幸いです。

今回挙げた、

- コードリーディング
- イメージを落とし込む力
- 手抜きのスキル

というの以外にもエンジニアとして重要なスキルとかは沢山あると思いますし、「自分に合う/合わない」はあると思います。ので、色々な要素をレゴブロックのように組み合わせて「自分なりのエンジニア観」みたいなのを作っていくのが実は一番大事かもしれませんね。

長々とした文章になってしまいましたが、少しでも新人の方の糧となれば幸いです。