主にプログラミングに関して。Python, .NET Framework(C#), JavaScript, その他いくらか。
記事にあるサンプルやコードは要検証。使用に際しては責任を負いかねます

スポンサーサイト

                
tags:
上記の広告は1ヶ月以上更新のないブログに表示されています。
新しい記事を書く事で広告が消せます。

JavaScript: thisの振る舞いに関して

                
tags: JavaScript
setTimeoutやsetIntervalを呼び出したときにしていたthisの勘違いについて
メソッド?とthisの振る舞いと

 JavaScriptのthisの振る舞いに面食らってから、コーディングで間違えを犯さないように考えを書いてきた。今回は電車でボーッとしていたらそのあたりがなんでそんなことになっているのか見当がついたので、それをまとめる。

 ぼく個人としてはJavaScriptは好きな言語だ。人にプログラミングを基礎から教えるときに楽。ブラウザさえあればOSがどうとかってことは気にする必要がないし、PCやスマフォを持っている人は実行環境をすでに持っているとみなせる。
 最近の言語はほとんどオブジェクト指向であって、さらにそれらはクラスベースである。オブジェクトを理解しなければ使いこなせないが、クラスベースのオブジェクト指向言語は基本的にクラスを書かなければオブジェクトを得ることができない。JavaScriptはブレース"{}"を使えば、クラスを経由せずにそのままオブジェクトが書ける。動的言語らしく動的にオブジェクトが書ける。少なくともオブジェクトの概念を教えるには余計なものがついてこない。

 JavaScriptを嫌う人はボチボチ見かける。ク○言語だという人がいるし、そんな意見の具現化としてCoffeeScriptやらが生まれてきたんだろう。で、嫌う理由をひも解いてみると、その中には「クラスがないから」ってのが入っている。あとthisがコーダーの意図するオブジェクトを指さないことがあるとか。
 JavaScriptにはクラスがない。代わりにプロトタイプがある。そのプロトタイプでは、親オブジェクトに変数や関数を与えておき、子となるオブジェクトには親オブジェクトのその変数や関数を参照させることで、使用メモリの増大を防いでいる。
オブジェクトは難しくない。難しいのはクラス

 上記のような仕組みのプロトタイプが実装されたことと、thisが初心者の予期しないオブジェクトを指してしまう理由はつながっている。thisは実行コンテキストによってどのオブジェクトを指すかが変わる(10.1.7 thisの項を参照)。
 子オブジェクトのもとで任意の名前のメソッドを実行しようとするとき("foo.method()")、親オブジェクトのprototypeプロパティに入れられた名前の一致する関数を参照してそれを実行する。この関数内のthisは子オブジェクトを指す。だからあたかもその関数が子オブジェクトのメソッドかのようにふるまう。ここでもしthisがオブジェクトと厳密に結びついていて、実行コンテキストではなく定義されたコンテキストで指すオブジェクトを決定するものになっていたら、子オブジェクトのメソッドを実行しても、メソッド内のthisは親オブジェクトを指すようになってしまう。プロトタイプが成り立たなくなってしまう。そういうわけでthisは、プロトタイプを実装するために実行コンテキスト依存の仕様になっているわけだ。
 ちなみに途中で簡便のためメソッドという言葉を使ったが、メソッドというものはJavaScriptにはない。これもクラスベースでやってきた人には嫌われる仕組みかもしれないが、やっぱりプロトタイプでやるための仕様なんだろう。
            

コメントの投稿

非公開コメント

プロフィール

hMatoba

Author:hMatoba
Github

最新記事
リンク
作ったものなど
月別アーカイブ
カテゴリ
タグリスト

検索フォーム
Amazon
上記広告は1ヶ月以上更新のないブログに表示されています。新しい記事を書くことで広告を消せます。