JavaScriptの生きてるundefinedと死んでるundefined
JavaScriptの悪魔的な振る舞いの一つにundefinedがあると思う。
javascriptには存在するundefinedと存在しないundefinedがあるし、それはつまり [undefined].length => 1 だ
— 俺は平気だよ (@mizchi) 2014, 4月 22
JavaScript、[undefined].length => 1 で arr = []; arr[0] = undefined; だけど、このとき前者のundefinedと後者のundefinedは性質的には別物ですよ
— 俺は平気だよ (@mizchi) 2014, 4月 22
もう一つの例として、 obj = {}; のとき obj[‘a’] = undefined したとき、for i in obj するとイテレータが一回だけ回る。obj[‘a’] = undefined しても キーは消えない。delete obj[‘’a] のときやっと消える。
— 俺は平気だよ (@mizchi) 2014, 4月 22
(最後のはobj['a']のタイポです。)
どういうことかというと、こう
var obj = {}; obj.a; //=> undefined for(var i in obj) { console.log('iterate'); //こない } obj.a; //=> undefined obj.a = undefined; for(var i in obj) { console.log('iterate'); //くる } obj.a; //=> undefined delete obj.a; //消した for(var i in obj) { console.log('iterate'); //こない }
僕の理解の範囲だと、ハッシュは値がundefinedなキーを定義できるので、Object.keys({a: undefined}) は['a'] という感じ。そんでArrayはObjectのサブクラス。
ちなみに javascriptのundefinedはなぜか予約語じゃないので代入できる。nullはできない。
> null = 3 ReferenceError: Invalid left-hand side in assignment > undefined = 3 3
ただsetterが定義されてないので実体が書き換わることはない。
追記
自分で明示的な「無い」を表現したいときはnullを使うのがいいと思っている。 たとえば listからidが一致したものを探す findById を実装するときは
var findById = function(list, id){ for(var i in list){ if(list[i].id === id) return list[i]; } return null; }
みたいにnullを返すことを明示しておけばよい。なぜならjavascript処理系は基本的にnullを暗黙的に生成することはほとんどないので(まったくないかは調べないとわからない)、これは人工的な値なんだなということがわかる。