2012-11-07
■ [web] Advent Calendarの季節が近づいて来ました
毎年恒例になってきた感のあるAdvent Calendarですが、今年はもう11/1の時点で企画が立ち始めているようです。 12月のイベントなのに気が早いとも思いますが、何を書くか考える余裕があってそれはそれで良いかもしれません。
ということで、前から気になっていたNAVERまとめで一覧を作ってみました。
とりあえず言語+ジャンルで分類しています。
例年はATNDあたりで立てる人が多かったですが、今年はAdvent Calendar専用サービスや、 Qiita上でのホスティングなどがあり、より簡単に企画を始められそうです。 Advent Calendarはコミュニティの活性化、情報共有、人材発掘などいろんな効果があるので、技術系に限らずいろんなジャンルの Advent Calendarができるといいですね。
2012-11-15
■ [sinatra] Sinatraでなんかつくるときのテンプレート的なものを作った
Sinatraで何か小さなものをさくっと作りたいときに、Gemfile書いてディレクトリ作って…とかするのが面倒なので、 テンプレ的なものを作りました。
ビューはSlim、CSSはSassを使うようになっています。ここらへんは単純に好みです。
最初のリポジトリをcloneすると、とりあえずrackupでアプリが動く状態になっているので、動作を見ながら作業を始めることができます。 forkして、自分の好きなGemを入れておくと良いでしょう。
で、これを使って作ってみたのがこちら:
先日のAdvent Calendar 2012まとめの更新のために手元(localhost:4000)で動かしているアプリです。
ちなみに
Railsの場合はApplication Templateが同じ用途に使えます。rails new後に行うカスタマイズ作業を自動化するものです。
2012-11-17
■ [altjs] CoffeeScript、TypeScriptにおけるthisのスコープ問題への対処
JavaScriptでは「this」はダイナミックなスコープをもつ。このことはたまにバグの原因になる。例を挙げよう。
var Animal = function(name){
this.name = name;
$("#animal").click(function(){
$(this).text(this.name);
}
};
問題になるのは4行目の「$(this).text(this.name)」で、このfunctionが呼ばれる際にはthisはDOM要素を指しているため、「this.name」でAnimalの名前を取ることはできない。
解決策としては、以下のように_thisとかselfのような適当な変数を作って、外側のthisにアクセスできるようにしなければならない。
var Animal = function(name){
this.name = name;
var _this = this;
$("#animal").click(function(){
$(this).text(_this.name);
}
};
jQueryやunderscore.js等にはjQuery.proxyや_.bindという関数があり、あるfunctionのthisを固定することができる。今回のように両方のthisを使い分けたいケースには利用できないが、 たいていのケースには役に立つだろう。
CoffeeScript
さて、CoffeeScriptに代表されるJSにコンパイルされる言語 (いわゆるaltjs) (Advent Calendarもあるよ) (いま参加者6人です) では、thisのスコープ問題に関して独自の構文をもって対応することが可能である。 CoffeeScriptとTypeScriptについてその挙動を調べてみたので、ここにメモしておく。
CoffeeScriptでは、通常の「->」の代わりに「=>」を使って関数式を記述した場合に、自動的に「_this」を定義するという機能がある。
しかし、以下のように「@」ではなく直接「this」と記述した場合も、_thisに置き換えられてしまうようだった。この仕様だと、今回のようなケースでは手で_thisを定義してやる必要があるため、注意が必要だ。
Animal = (name) ->
@name = name
$('#animal').click =>
$(this).text(@name)
もう一点、functionがネストするケースについても調べてみた。
Animal = (name) ->
@name = name
some_func =>
$('#animal').click =>
$(this).text(@name)
- some_funcとclickの両方が「=>」のとき:thisおよび@はanimalを指す。
- some_funcが「=>」でclickが「->」のとき:Animalのところにvar _this=this;が入るが、thisおよび@は_thisに差し替えられないため、DOM要素を指す。
- some_funcが「->」でclickが「=>」のとき:some_funcに渡すfunctionのところにvar _this=this;が入る。
- some_funcとclickの両方が「->」のとき:thisおよび@はDOM要素を指す。
TypeScript
次に、Microsoftの開発したaltjs言語、TypeScriptについても見ていこう。 TypeScriptはJSとの互換性をかなり意識して設計されており、おそらくaltjsではトップクラスに綺麗なJSを出力する (まあ出力されたJSを手作業でメンテしたいかと考えると、そういうシチュエーションは避けたい気がするが、生成物の挙動が理解しやすいというメリットはあるかも)
話がそれたが、TypeScriptにおけるthisについて調査する。 最初は特に何もしてないのかと思ったが、「() => { alert(this) }」のような形の関数式を使った場合のみ、thisの差し替えが起こるようだ。これに関しては 仕様(PDF)の 4.9.2 Arrow Function Expressionsに書かかれている。
Playgroundで試すと、CoffeeScript同様「var _this = this;」を挿入する方式のようだ。
$("#animal").click(() => { alert(this.name) });
のようにすると、thisが_thisに差し替えられる。 CoffeeScriptと同じく、2種類のthisを使い分けたい場合は手作業が必要。
ネストしたケースについても調べておく。
some_func(() => {
$("#animal").click(() => $(this).text(this.name));
});
- some_funcとclickの両方が「=>」のとき:thisおよび@はanimalを指す。
- some_funcが「=>」でclickが「function」のとき:var _this=this;の挿入は行われない。thisおよび@はDOM要素を指す。
- 挿入が行われないのは、some_funcに渡すコールバックで「this」を使っていないため。つまり差し替えを行うのは「=>」の直下のthisだけらしい。
- some_funcが「function」でclickが「=>」のとき:thisおよび@はanimalを指す。
- some_funcとclickの両方が「function」のとき:thisおよび@はDOM要素を指す。
ということで、内側だけ「=>」を使った場合の仕様がCoffeeScriptと異なる。
まとめ
CoffeeScriptの「=>」は「thisを一つ外側のthisにする」という機能だが、 TypeScriptの「=>」は「thisを現在のインスタンスにする」という機能である。
これから自分のaltjsを作ってみようと思っている人は、このあたりの仕様も考えてみると面白いだろう。
(JSXとHaxeは調べてないですが、何か機能があったら教えてください)
ちなみに
次世代のJavaScript仕様(EcmaScript6)になるべく議論が重ねられているES Harmonyにも、「=>」の導入が含まれているようだ。
まだ策定段階なのでなんとも言えないが、こっちの「Maximally minimal class」の中で「=>」を使ったときの仕様がCoffeeScriptのようになるのか、TypeScriptのようになるのかは気になるところである。(なんとなく、前者になりそうな気がするけど)
2012-11-20
■ [ruby] EventMachineで大量のソケットをつくろうとしたらbuffer overflow detectedになった
こういうやつ。
*** buffer overflow detected ***: ~/.rvm/rubies/ruby-1.9.3-p194/bin/ruby terminated ======= Backtrace: ========= /lib/x86_64-linux-gnu/libc.so.6(__fortify_fail+0x37)[0x7f2ed0626007] ...
これはエラーメッセージが微妙で、EM.runの前にEM.epollを呼ばないとそうなるのだそうだ。
2012-11-28
■ [ruby] Rubyアドベントカレンダー2012
Rubyのアドベントカレンダーが立てられたようです。
例年補欠が出たりしているので、何かネタのある人は11月のうちに登録しておくと良いかと思います。
Ruby関係ではもう一つ、RubyMotionのが企画されているようです。
□ mori_dev [> jQueryやunderscore.js等にはbindという関数があり、あるfunctionのthisを固定する..]
□ yhara [あ、jQuery.bindはイベントの関数なんですね…。ありがとうございます。]