転職した

調べた事、学んだ事、思った事、考えた事を個人的にまとめているだけなので内容は保証しないYO!

Vimのmap、noremapについて調べた

mapやnoremapはあるキーを別のvimコマンドに割り当てることができる機能

:map z x

を実行すれば、zを押した時xが実行される(ノーマルモードなら1文字削除される)。

:map yyyy 2dd3p

のように、1文字対1文字である必要はなく、複数文字でよいし、実行するコマンドも複数のオペレータコマンドを使える。 ここはnoremapも同じ。

mapとnoremapの違い

一言で言えば、mapはmapが連鎖するが、noremapは連鎖しない。

:map x p
:map z x

このexコマンドを実行した後にzを押した場合、pが実行される。z->x->pとコマンドを辿って終端のpがvimのコマンドとして実行されるわけだ。

noremapの場合は、このような事はおきない。

:noremap x p
:noremap z x

このexコマンドを実行した後にzを押した場合は、xが実行される。noremapはz->xと辿った後、さらにたどることはせずに、xをvimのコマンドとして実行する。

参考:【図解Vim】mapとnoremap | ここぽんのーと

mapやnoremapの種類

vimにはモードがあるため、mapやnoremapも各々のモード用に種類が存在する。

      コマンド                    モード
 :map   :noremap  :unmap     ノーマル、ビジュアル、選択、演算待ち状態
 :nmap  :nnoremap :nunmap    ノーマル
 :vmap  :vnoremap :vunmap    ビジュアル、選択
 :smap  :snoremap :sunmap    選択
 :xmap  :xnoremap :xunmap    ビジュアル
 :omap  :onoremap :ounmap    演算待ち状態
 :map!  :noremap! :unmap!    挿入、コマンドライン
 :imap  :inoremap :iunmap    挿入
 :lmap  :lnoremap :lunmap    挿入、コマンドライン、Lang-Arg
 :cmap  :cnoremap :cunmap    コマンドライン

引用元:Vim documentation: map

調べる必要のあったものだけ、説明を付け加える。 smapとsnoremapはビジュアルモード時に<ctrl-g>を入力した場合とノーマルモードでghと入力した場合に移行するセレクトモードでキー動作を変更したい場合に使う。 セレクトモードでは、印字可能文字を入力することになるので、mapするキーは印字可能文字でない文字がよい。

参考:Vim documentation: map

omapやonoremapはノーマルモードでdやyを入力したときになる演算待ち状態モードでキー動作を変更したい場合に使う。 なので、map先はモーションコマンドになる。

lmapやlnoremapは挿入モード、コマンドラインで<ctrl-^>を入力することで有効になるmapの設定。

参考:Vim documentation: map

vimを+rubyにする(MacOS, Ubuntu, CentOS)

達成目標:MacOS, Ubuntu, CentOSvimを+rubyにする。

MacOS

homebrewからインストールすれば+rubyになる。

 brew install vim --with-lua --override-system-vi

オプションの一覧は

brew options vim

参考:home brewでruby,perlオプションを有効にしてvimをインストール - Qiita

Ubuntu

デフォルトだとSmall versionが入ってる。vim-noxをインストールすれば+rubyになる。なお、Ubuntuのバージョンは14.04で行った。

sudo apt-get install vim-nox

参考:Installing vim with ruby support (+ruby) - Stack Overflow

CentOS minimal

デフォルトだとSmall versionが入ってる。 コンパイルが必要。下記はインストール直後のminimalから+rubyにするまでの手順。なお、CentOSのバージョンは6.5で行った。

yum install wget

# gccなどをインストールするため
yum groupinstall 'Development tools'

# ncurses-develを入れないとconfigureで下記のようなエラーになる
# no terminal library found
# checking for tgetent()... configure: error: NOT FOUND!
# You need to install a terminal library; for example ncurses.
# Or specify the name of the library with --with-tlib.
yum install ncurses-devel

# rubyとruby-develをインストールしないと+rubyにならない
# rubyについては、rvmとかでインストールすれば問題ないやも。
yum install ruby ruby-devel

cd /usr/local/src/
wget ftp://ftp.vim.org/pub/vim/unix/vim-7.4.tar.bz2
tar jxf vim-7.4.tar.bz2
cd vim74
# とりあえず、rubyinterpだけ。pythonとかperlとかはお好みで。
./configure \
--with-features=huge \
--enable-multibyte \
--enable-rubyinterp \
--enable-gpm \
--enable-cscope \
--enable-fontset

make
make install

参考:Cent OS でVimをperl, python, rubyオプション付きでインストール - 僕のYak Shavingは終わらない

参考:CentOS6にvim-rubyをインストールする - hidemium's blog

Rubyのifで=を使った時に警告がでるときでないとき

Effective Ruby

この例のようにif式の条件部で代入 することは一般的である。逆に言えば、本当は"=="を使うべきところでうっかり"="を使ってしまうこともある。この種のミスには気をつけたい

Effective Ruby p7

と書かれていて、あれ、ifで=を使ったら警告でなかったっけ?*1 と思って調べてみた。

#!/usr/bin/env ruby -W -v

a = 0
if a = 1
end

b1 = 1
b2 = 1
if b1 = b2
end

if $c = 1
end

d = 0
if d = 'hoge'.match(/hoge/)
end

e = 0
if e = 'hoge'.upcase
end

class Hoge
  attr_accessor :f

  def g
    if @g1 = 1
    end
  end
end

hoge = Hoge.new
if hoge.f = 1
end

hoge.g

h = nil
puts h = false ? 1 : h.class.to_s

このようなコードを実行してみる。最後の例は、下記のコメントで指摘されていたので入れてみた。

if式 / if文 の条件節で、左辺に定数を書くべき言語はあるか? @ajiyoshi.gist

実行結果は下記の通りである。

ruby 2.1.4p265 (2014-10-27 revision 48166) [x86_64-darwin14.0]
./hoge.rb:4: warning: found = in conditional, should be ==
./hoge.rb:12: warning: found = in conditional, should be ==
./hoge.rb:27: warning: found = in conditional, should be ==
NilClass

この通り、下記の場合しか警告がでない。

if x = 1
end

if $c = 1 
end

  def g
    if @g1 = 1 
    end 
  end 

条件演算子の例については、見ての通りで、演算子の評価順の問題である。y = falseが先に評価されるのであれば、FalseClassと出力されるはずだが、そうなっていない。というか、val = bool ? a : bという代入はCなどではよく使われるので、考慮不足な指摘な感じが否めない。

まとめ

警告がでるのは下記の場合に限られる(ようだ)。

  • 左辺が変数であり、右辺が1や'hoge'のような即値の時の代入

ゆえに、下記のような場合は警告がでない。

  • 右辺が即値でない場合
  • 代入メソッドの呼び出しの場合

右辺が即値の場合、絶対に実行されるか、絶対に実行されないのいずれかになるため、ミスの可能性が極めて高いといえる。ゆえに警告がでるのは妥当だろう。 ところが、代入メソッドの場合、右辺が即値でも警告はでない。代入メソッドの戻り値によるからかと思ったが、代入メソッドは引数で指定された値を返すという挙動をする。つまり、puts o.v = 1とした場合、o#v=(v)で何を返していても1が出力される。なので、代入メソッドの場合も警告がでる方が妥当だと思うのだがなぜかでない。よく分からない挙動である。

Effective Ruby

Effective Ruby

SIerから非SIerに転職して2ヶ月たった

正確には2ヶ月と1週間だけど。SIerから足を洗ってソフトウェアハウスに転職した形になる。SIerもソフトウェアハウスも定義が曖昧で何がなんやらという感じだが、「派遣、ITゼネコン、SES」とかそういうワードばかりの会社から、そういうワードのない会社にした。SIerといっても、みかかデータみたいな大手じゃなく100人程度の派遣メインの弱小SIerだ。

今回の転職は成功だったかといえば、まあ、成功だと思う。歯切れの悪い感じなのは100%満足の転職なんてそうそう無いし、今回の転職も例にもれず、そうだからだ。

今の会社に転職して良かったと思える点をあげると、

ガチでできる人ばっかりで勉強になる

前の会社では、「技術力がある」と評価を受けていたが、そんなもんまるでなくて、「はてなとかクックパッドみたいな有名企業のエンジニアからすれば『戦闘力・・・たったの5か・・・ゴミめ』と言われるようなレベル」というのが前職の同僚との自己評価で、それは間違ってなかった。今の会社じゃ自分の技術力なんて本当にゴミ。

他にも、考え方とかやり方とか技術に関係ない部分で勉強になることも多い。

デスクがやばい

机がでかい。90x180ぐらいある。椅子もやばい。ハーマンミラーとか普通に置いてある。おかげで腰痛がかなり改善した。端末もやばい。Core i7、メモリ32GB、HDD3TBとか。つーか、元サーバ機。ラップトップもつく。ディスプレイもやばい。ディスプレイアーム付きでデュアルディスプレイ。ラップトップがあるから実質トリプルディスプレイ。

椅子がよくなったのが本当に嬉しい。前職の椅子の形をしたなにかが、腰破壊マシーンでしかなかったことを再確認した。

なんかもう、いろいろいい加減

就業規則に「泥酔しての執務禁止」と書いてあるらしい(らしいというのは、就業規則というものをお目にかかったことがないから。ファイルサーバが死ぬまで、そこに存在したらしいのだが・・・)。ていうか、コーヒー1杯10円みたいな感覚でカクテル用のウィスキーが置いてある。飲んでるところは、見たことないけど。 こういう感じなので、仕事が進むなら何しててもお構いなしという感じである。

悪かった点を挙げるなら、

ChatWorkが本当にうるさい。Stashもうるさい。朝会も夕会もうっさい。

これは、他の人がなんで仕事進められているのか本当に疑問に持つレベルなのだけど、ほんとーにうるさい。Chatworkのプロジェクトグループでは、自分と関係ない話題が続き煌煌と未読のバッチがつく。そうかと思えば、突如自分宛のメッセージが飛んできてしばらく無視していいのか、即応した方がいいのか判断がつかず直前のやりとりを読まねばならず、軽くやりとりした後は、はて何をしていたのだろうかと思い出す羽目になる。電話割り込み並みにうっとおしい。

StashというのはAtlassianの製品で、GitHubみたいなツールである。で、何がうるさいかといえば、Pull Requestのレビュー結果がメールで通知されるので、「ああ、見て修正しなくちゃ」と思ってしまう。メールなんてほっといてもよいものだが、Pull Requestのレビュー結果メールだから明確にアクションが必要なメールなわけで、やっぱりうっとおしい。

朝会も夕会もうるさい。朝会はスタンダップミーティングとか言われるあれで、今日は何やります、かにやりますというあれ。夕会は今日は何やりました、かにやりました、これで困ってますというあれ。別に悪いことじゃないし、いいんだけど、集中力をぶっ飛ばす効果もテキメンで、うっとおしく感じてしまう。

文句をだらだら並べたけど、全部、集中力破壊系で、要するにいつのタイミングにおいてもフロー状態になれない。言うまでもなく、プログラマにとっては致命的な問題で、対策を打たねばならない。この問題に気付くのに2ヶ月かかってしまったが。

SIerと非SIerを比較して

所属したことのあるSIerは2社(どちらも弱小)、派遣(偽装請負)されたことがあるのは5,6社(大小ある)だと思う。その中で思うのは、技術に詳しい人なんてこれっぽっちもいないということ。巡り会いが悪かっただけかもしれないが、戦闘力たったの5のゴミでも詳しい奴になってしまう場所ばかりだった。ランチェスター戦略的に言えば、パッとしないプログラマが強者に回るには格好の場所である。

ただ、SIerというのは、ちょっぴりのコンピュータ知識とたっぷりの業務知識でやっていく人が集まる場所だ。SIerにいる以上、業務知識がないのでは使い捨てられる未来しかない。

弱小SIerに所属するというのは二重苦で、コンピュータ知識もつかず、業務知識もつけられない。Javaで会計システムの開発をしていたと思ったら、次の月にはCでUNIX上で動くプログラムの開発に派遣されるなんてことはよくある。

何もかもが中途半端な状態で、30後半になって転職しようにもこれができますと言えるものが何もない事態に陥る。

そういう意味で、非SIerはかなりよい。自社でなんの技術を使うか決めるし、長い間とどまっている人がいるからノウハウも溜まっている。業務知識も同じだ。かなり深いレベルで一挙両得ができる。まあ、B2Cなら業務知識という概念もないだろうし、設立して日が浅ければ一挙両得なんてとても無理だろうけど。

ただ、SIerはむやみやたらと人の出入りが多いおかげで、全体の知識レベルや意識レベルが良い意味でも悪い意味でも均一になっている。やり方が良い意味でも悪い意味でも安定している。非SIerは人の流動性が低いために、良い意味でも悪い意味でもやり方とか知識、意識が独自進化しているため、うまくいっていない部分もあったりするんじゃないかと思う。

まとめると、潰しがきくことを望むならSIerはやめとくほうがいいんじゃないですかねってとこでしょうか。

地頭力を鍛えるを読んだ

地頭力を鍛える 問題解決に活かす「フェルミ推定」

地頭力を鍛える 問題解決に活かす「フェルミ推定」

レバレッジリーディング同様、先輩に勧められたため読んだ。

「昔は知識とコミュニケーション力でなんとかなったが、今の時代、思考力(この本でいうところの地頭力)をつけねばダメだ。地頭力の構成要素はフェルミ推定で鍛えられるから、フェルミ推定で訓練しよう」という論旨の本。

地頭力というのは、知的好奇心をベースに

  • 論理思考力
  • 直観力

があり、それらの上に

がある。これらの構成要素で地頭力は成り立っているというのがこの本の定義である。

はっきりと言ってしまえば、真摯にプログラマという仕事をしていれば、どれもこれも鍛えられる力で、抽象化思考力は「プログラミング」、フレームワーク思考力は「デバッグ、ドキュメント作成」、仮説思考力は「外部ライブラリの利用、他人のコード引き継ぎ」のタイミングで力がつくと思う。

フレームワーク思考力と「デバッグ、ドキュメント作成」

抽象化思考力と「プログラミング」は説明するまでもないだろうから、省略する。

そもそも、フレームワーク思考というのがピンとこないが、「全体から考え、部分に分解する。あるいは、部分にズームインしていく。こうすることで、思い込みや自分の立場など思考の妨げとなるものを排除できる。」ということらしい。

デバッグのうまい人も全体から考えて、無関係なところを排除してバグを追求するということをするので、鍛えるにはもってこいだろう。下手な人ほど、自分が意識している所ばかり、目がいってしまう。ドキュメント作成も、全体から考えて部分を構成していくとするはずである。下手な人は、思いつきで書き連ねてしまって、「この赤い矢印と青い矢印と緑の矢印は何が違うんだ? 凡例もないし・・・」とかなりがちである。

仮説思考力と「外部ライブラリの利用、他人のコード引き継ぎ」

仮説思考というのは、「いまある情報から仮説(目標)を立て、その仮説を目指しつつ、得られた情報から仮説の精度を上げて、最終結論を出す」という考え方。

外部ライブラリ(OSSフレームワークでも、プロプライエタリなライブラリでも)もプロジェクト内の他メンバのコードも、結局内部詳細がわからないというのは同じである。 なので、限られた情報から利用、拡張方法を考え、開発着手し、途中得られた情報から方法を修正して開発完了させるというやり方となる。というわけで、仮説思考力をつける良い方法であると思う。 ただ、仮説思考で開発するというのは、行き当たりばったりで危なっかしい。この本にも書かれているが、「限られた時間で、それなりの結果を出すための考え方」なので、常にこのやり方をするのはかなりまずい。

偉そうなこと言いつつ、仮説思考はできてないなーと思う。

見積もり = フェルミ推定

この本を読んで思った事は、ソフトウェア見積もりというのはフェルミ推定を行うということに他ならないということ。「日本の電信柱の数は?」と「A社の基幹システムの工数は?」という質問に対するアプローチは全く同じである。手元にある情報を元に、部分に分解して、部分がどの程度の数値になるか概算し、積算する。追加情報を得ることはできるとはいえ、情報が増えるだけで、やることは同じだ。

フェルミ推定では、前提や推論の方法の違いによって結論にかなりの誤差を生じることもある。

フェルミ推定 - Wikipedia

こうあるように、見積もりがフェルミ推定なら、工数200%とか発生してもなーんも不思議じゃないよなぁと。

まとめ

プログラマという仕事をしている人で、仕事を上手くこなす上で必要な抽象化思考力、フレームワーク思考力、仮説思考力をつけたいという人は買ってもよいのでは。

レバレッジリーディングを読んだ

レバレッジ・リーディング

レバレッジ・リーディング

普段、いわゆるビジネス書籍というのは読まない。理由は単純で、尊敬できる人が「このビジネス書よかったよ」と言っていたことが一度たりともなく、尊敬できない人が「この本はぜひ読むべきだ。社長にも全社員に読ませるべき本だと話しておこう」とか言っていることは、ままあったからだ。尊敬できる人の背中を追うならば、「ビジネス書は必要ないのだな」と考えるのは自然なことであった。 では今回なぜビジネス書を、それも8年も前の本を今更読んだのかというと、転職した先の先輩に勧められたから。私より技術に精通していて、頭もよい、ようするに尊敬できる先輩に。尊敬できる人に勧められては、仕方ない読むしかないね*1。徒弟制度にも基本賛成だしね。

内容

箇条書きで表すとこんな感じです。

  • 本を読むのは投資行為
  • 1500円そこらで他人の経験を追体験できるのだから安い投資
  • 書評サイトとかメルマガ使って選ぶプロセスを工夫
  • 目的をはっきりさせて、目的を意識して読む
    • 目的がはっきりしていないと、漠然と読むと時間がかかってしまう。しっかり読むべき所もだらだらと読んでしまって、意識に残りにくい。
    • 目的に関係ない所はすっ飛ばす
    • すっ飛ばした所に重要な事があるかもしれないがそれは割り切る
  • 小難しい本ではなく自分が読みやすい本を買う
  • 同じテーマでいろんな本を読む
    • 複数の人の視点から同じテーマについて読む事になるので多角的に読める
  • 読む価値ないはずれを引いたなと思ったらさっさと捨てる
  • 本は汚してなんぼ
    • 投資行為なのだから、折ろうが書き込もうがそれで効率よく投資回収できるならすべき
    • バンバン、蛍光ペンでマーキングして後で読んだときにすぐに場所が分かるようにすべき
  • マーカーしたところはパソコンなり何なりでまとめていつでも読み返せる状態にする
    • まとめ終わったら、本は出がらしみたいな状態になるから読み返す必要はない
      • ただ、幾度も読み返す価値のある本というのはある
  • 本棚にどういう順番、位置で本をおくか工夫して整理するとか

感想

この本はビジネス書を読む事と前提にしているのでコンピュータ系書籍で実践するのは難しいだろうと思う。 実践できるとしたら、自分の技術水準がかなり上で、スラスラ読んでいける状況になっていないと実践できないはず。Linuxの勉強をしたくてLinuxシステム[実践]入門を買ってレバレッジリーディングできるかといえば当然無理。でもRails3のプログラマがRails4の新機能を把握したいと思ってRuby on Rails 4 アプリケーションプログラミングを買ったならレバレッジリーディングはできると思う。あるいは、ビジネス書とあまり変わらないピープルウェアとかラピッドデベロップメント*2みたいな読み物系なら使えるかもしれない。

Linuxシステム[実践]入門 (Software Design plus) Ruby on Rails 4 アプリケーションプログラミング ピープルウエア 第3版 ラピッドデベロップメント―効率的な開発を目指して (MicrosoftPRESS)Amazonへのリンクです

レバレッジリーディングを途中からレバレッジリーディングしながら読んだので読み落としてる所があるかもしれないけど、仕方ないね:-P

*1:おかげさまで、技術書を読む暇がしばらくない(;´Д`)

*2:Amazonに新品がないけど、もしかして、ラピッドデベロップメントって絶版なのか?

アジャイルソフトウェア開発の奥義を読んだ

アジャイルソフトウェア開発の奥義 第2版 オブジェクト指向開発の神髄と匠の技

アジャイルソフトウェア開発の奥義 第2版 オブジェクト指向開発の神髄と匠の技

OOPを勉強するのに良いと勧められて買った本。かなり内容が濃い本で600ページにも及ぶため、読み進めるのに苦労した。完全に消化不良なので機会を見つけて読み返すようにしたい。 ただ消化不良なりにもいくつも発見があって、

といった事について気づきがあった*1

アジャイルソフトウェア開発とはなにか

この本を読んだ事でアジャイルソフトウェア開発とはなんぞやということに対してようやく答えが見えた気がする。今まで感覚でしか理解できていなかったことだけど、アジャイルソフトウェア開発というのは変更に強いようにコードを構築し続けていくから変化に対応できるのであって、顧客からの要求をすぐに取り込んですぐに修正をしたからといってアジャイルソフトウェア開発ではないしカーゴカルトにしかならないという事が明確になった(書いてみれば当たり前のことだ)。そして、変更に強いコードを書くためにSOLID原則やデザインパターンを理解したスキルの高いプログラマが必要で、そういうプログラマを集められないならアジャイルソフトウェア開発なんて実践不能だと理解した。

テストコードをうまくかけない根本原因

白状すると手動テストがメインの開発しかやった事がない。言い訳させてもらえれば、テストコードを書こうとしたりTDDを実践しようとテスト駆動開発入門を読んだりしてはいたのだが、なぜか面倒な事になってしまいうまく実践できなかった。なにかテストコードを書く方法についてわかっていないことがあるのではないかと思っていたが、それはまったくの間違いで、設計が腐っていたことが根本的な原因だと理解した。試しに個人的に作ったツールリファクタリングしてみたが、ごちゃごちゃと処理が放り込まれたクラス(単一責任の原則に明確に違反している!)ではテストコードを書くことなど不可能であったが、単一責任の原則を意識しつつクラスを分解してみればテストファーストを実践する事ができた。

デザインパターンはやはり重要ということ

また白状するとデザインパターンをまともに勉強した事がない。やはり言い訳させてもらえれば、前職が色々アレで優先順位が低かったせいである。Template Methodパターンとかいっても通じない人しかいないので勉強するメリットが薄かったし、Template MethodパターンやFacadeパターンなどは勉強せずとも実践していてその時々でうまい設計をひねり出せるだろと考えていた。しかし、改めてデザインパターンを学ぶとTemplate Methodパターン脳をこじらせていることに気づき、「このクラスとこのクラスで必要なメソッドがあるな、Abstractクラスつくるか」という思考にはまっていて、こういったこじらせたものを改善するためにもデザインパターンは学ぶ必要があるなと思った。

まとめ

OO歴数年目の中級者が上級者に上がるのには最適な本だと思う。我流で間に合ってるしなぁと考えている人には確実にステップアップに繋がるし、アジャイルな開発に近づくことができるはず。もし、初級者がGoFが必読と言われているからという理由で買おうと思っているならこっちを買った方がまだ身になるだろう*2

*1:他にも、Fat ControllerやModel==ActiveRecordな人はMVCではなくOOを理解できてないのではないか等思ったけど、省略。

*2:この本はJavaC++のサンプルコードだがGoFSmalltalkなはず。どちらにせよ初級者には向かないと思うが