「パーフェクトJavaScript」メモ 5章 変数とオブジェクト

編集モードをはてな記法にした。

変数にオブジェクトを代入すると、変数にオブジェクトの参照が代入される

原文ママ。一見日本語がおかしいようだが意味はわかる。参照渡しなので以下のような動きをする。

>var a = { x:1, y:2 };
>var b = a;
>b.x++;
>print(b.x);
2
>print(a.x);
2

a か b に新しいオブジェクト値が渡されない限り彼らは同じものを見続ける。bののぞき穴からオブジェクトの値を変更した後も、同じものを見続けている彼らからは同じものが見える。

var one = 1;
var zero = 0;
function swap(a,b){
  return [b, a];
}

しかしこれ全然わからない。これでなぜ one と zero の値が入れ替わるのか
引数と関係があるのかreturnと関係があるのか。関数の項を見ればわかりそうだけど。

jsの変数はプロパティそのもの

まじか

関数から抜けた後もアクセス可能なローカル変数がある
クロージャとして後ほど説明がある

よろしくお願いします

undefined値に対してプロパティアクセスするとTypeError
単に存在しないプロパティを呼ぶだけだとundefinedが返ってくるだけ

これはよく思い知らされる

オブジェクト指向の説明はいろいろなプログラミング関連書籍に出てくるけど、どれも自分がエアマスターを人に薦めるときのような語り口になってる。
すなわち、言いよどみながらも以下の内容を含んだ文章を述べる。
「宗教や思想のようなものである」
「説明は抽象的にならざるをえない」
「いろいろとアレであるが」
「いいものである」
「よさを一言で表すのは難しいが」
「いいものである」

引数をオブジェクトリテラルで渡すのは以下の点で優れている
・名前付きで渡せる引数の順番を間違えにくい
・引数()部分の記述が短くて済む

いいですね

「コンストラクタ代わりの関数での利用法」の項、全然わからない。まずコンストラクタがよくわかっていないので。
と思ったらすぐ後にコンストラクタとnew式の説明があった。
しかし、これも全然さっぱりわからない。どうした。
これは「コンストラクタという概念が入っていないとコンストラクタの説明を読んでもコンストラクタがわかるようにならない」という一見矛盾めいた真理の現前なのではないか。
おそらくArrayとか使ったことなければArrayの項を読んでも意味がわからないだろうが自分はわかった、それがコンストラクタでは効かなかったのだ。

コンストラクタについてわかったこと
・コンストラクタは 常にnew式で呼び出す
・コンストラクタは常に、同時に関数である。すなわち関数の一種である。コンストラクタとして意図した関数を「コンストラクタ」と呼んでいる
・コンストラクタ内には return文をかかないようにしましょう

コンストラクタについてわからないこと
・どういうとき使うのか
・なぜ使うのか
・なんなのか

以上。とりあえず先に進む。

数値をキーに値をひけるデータ構造を一般に配列と呼ぶ

そこが配列のキモだったのか。「順番がある」かと思ってた(同じこと?)。

この定義でいくと連想配列は配列ではないということになるな。

で、連想配列はハッシュと呼ばれることもあるしマップや辞書と呼ぶこともあるが、この本では連想配列と呼ぶらしいです。

オブジェクトを連想配列として見る・使うことが可能なだけで、連想配列用の何かが用意されているわけではない

この辺の説明は自分に自然に受け入れられた

プロトタイプ継承もわからないので、こののち説明が出てくるようなのでそのときまで理解をおあずけ。
うお、と思ったがすぐここからプロトタイプチェーン、プロトタイプオブジェクトと話が続くのか。
本書で初めて数ページにわたりつまずいたぞ
「Aを使いたいとか、Aとは何なのか知りたいとかいった欲望を持たない人に対して『Aとは何か』を説明しても理解できない」と一般化できるか。

いつまでも素人でいたい(都合のよい名ゼリフを思いついたので言う)

ここでここから先7ページほどの記述を読み飛ばすのは得策か否か。
結論→字面だけ読んでみよう。

どうやらコンストラクタやクラスといった、プログラミングにおける初歩的な道具に対して理解がないと厳しそうだ。
クラスがまだいまいちのようだ。他の言語を少しでもやっているとここで足踏みしないかもしれないな。

能書きが長くなってしまったな。

p137,138の見開きで最初に「光が差した」かなと思った一文がこちら

プロトタイプチェーンによりすべてのオブジェクトは最終的にObject.prototypeオブジェクトへの暗黙リンクを持ちます。

これはなんとなく世界の想像をしやすくしそうな文。

で、あまりにわからないので以下のコードをブラウザのコンソールに書く。

>function MyClass(){ this.x = 'aaaa'; }  
>var obj = new MyClass();
>obj 

結果は
f:id:stand-ooc:20160927235606p:plain
あー、newで変数に関数を代入すると、明示的に作ったオブジェクトの他にプロトタイプもくっつきますよということですかね。

あとは使いどころがわかればパッと道が開ける気がしました。先に進もう。

__proto__は暗黙リンク先のオブジェクトを参照しています
__proto__プロパティは、ECMAScriptの仕様にはない実装依存の存在です

そうだったのか

なんとかプロトタイプの項を抜けた。

var d = new Date();

もしかしてこれコンストラクタでした?(もしかしてもなにも、そうか。)

「5-17 オブジェクトと型」の項、オブジェクトの型判定の話から始まっているが「オブジェクトにとって型とは何か」「どういうものが考えられるか」が全然書いてないので自明なんだろうな(しかし、全然イメージできていない)。

というわけでググった
qiita.com
ArrayとかFunctionとかJSONとかDateとかErrorが型と呼ばれるものに該当するようだ。
上の記事での型判定の記述、パーフェクトJavaScriptの記述に共通しているところが多々あるので安心する。世界はつながっていた

for in 文もfor each in 文もin演算もプロトタイプチェーンをたどります

そうなのか。困ったことはないが。意図してないのに辿られたら困るんじゃあないのか(今日ジョジョ見た)

「5-17-5 プロパティの列挙(プロトタイプ継承を考慮)」を見ると、p130のプロパティの属性の説明でenumberable属性の意味を「for in 文で列挙可能」と書いてあるのは本質的な説明ではないようだ。 例えば、keysで拾えるかどうかにも関わる。

アクセッサ属性

この章のこの記述だけではちょっと何もわからない。ゲッターとセッターは非常によく使うしぜひ仕組みを理解しておきたいところだが

「5-19 標準オブジェクト」ArrayクラスやDateクラスといったオブジェクトの型の列挙、してくれてました。ありがとうございます。

Object.prototypeオブジェクトにプロパティを追加すると、あらゆるものにプロパティが追加される

笑った。仏教のよう

Object.prototypeオブジェクトのプロパティの列挙、とてもありがたい。今までただの(邪魔な)文字の羅列であった。そこに意味が与えられる。光差す。
しかし今は流し読みさせていただきます

「◯◯は宗教である」「これは宗教論争である」といった文の意味って明確なのだろうか。解釈に幅がありそう。
しかし、数ある解釈を包含した意味をこれらの文が持っているとすれば、問題ないような感じもする。(完全な脱線)

唐突にMathオブジェクトとErrorオブジェクトの説明が(グローバルオブジェクトの説明の後に)あるが、このふたつが特殊なのか、なぜここで特にとりあげられたのかが不明だ。それが明らかになるのはいつの日か、乞うご期待

5章終了。

「パーフェクトJavaScript」メモ 4章 文、式、演算子

4章の前に。 

「配列はArrayクラスのインスタンスとして存在します」この一文を解読できない。

「パーフェクトJavaScript」メモ 1章,2章 - reopon.hatenablog

 昨日自分はこう言っていたが、3章でArrayクラスとはなんぞやということとインスタンスという語の用法がわかったので、まったく引っかかるところのないあたりまえ文章だとわかりました。成長、それは

で4章「文、式、演算子」。

文は文と式から構成され、式は式と演算子から構成される。

 こういう文章は整理に役立ちそうなのでメモっておく。

最小単位は識別子(変数名・関数名)、リテラル値(直接表記)、演算子(記号・予約語)

 額面だけ見ればわかりやすい。

なんだ「将来の予約語」って。2011年(第一刷発行年)以降に予約語になるということですか。 

リテラル表記」とは、コード上に書いた値が実行時にその値そのままの意味を持つ仕組みのこと

 そうなんだろうけどこうやって端的に説明してくれるといいですね

(この世に「いい本を書くぞ」「売れる本を書くぞ」という人が複数いて、それぞれがそれぞれいいと思う書き方で本を書いて出版するの、どうなんでしょうか。過渡期か)

(例えばJavaScriptに関する本をの「JavaScriptの本」というひとつの本のバリエーションとしてバージョン管理するとか……なんか言葉にしてみると異様に魅力がなくなっていた)

(再掲)if文の条件式に書いた式の評価結果はブーリアン型に型変換されるので注意

気をつけよう。

else の後にまた条件式が連なる場合 else if となるのは、ブロック文にしないでそのままコードを書いた様子であって、 それ自体が特別な記法というわけではない

 あー。そっかー。else と if の間にスペースあるかないか迷ったことあるけど、elseif という特別な節があるわけではないのでもう間違えませんね

ほか、繰り返し文の場合でも、中括弧で括らなくても成立しているようだ。ただ実行順でまずいことになるので明示的に中括弧で括る(ブロック文にする)と。

while文、実際に使ったことない。これどうなのやばいの

n = ~~(n / 10);  //~~演算は小数を整数にする(トリッキーな)技法

知らなんだ

「スコープ」の項をはやく読みたい。全然わかっていない。

for in 文で列挙されないプロパティ、たとえば length があるが、これはプロパティの属性に依っている。

そうだったのか。全然構わずfor in 文を使っていた。

break ラベル; や continue ラベル; でラベルのついた繰り返し文から抜けられる

便利だ

with文、存在意義がわからなかったが、非推奨らしいので覚えないぞ。

演算子をオペレータ、被演算数をオペランドと呼ぶ

用語「オペランド」が整理されました。ありがとうございます。

「オペレータ」「被演算数」はこの後ほとんど出てこないようです。 

||演算子、&&演算子三項演算子の3つの演算子のみ遅延評価をする

依然ruby推しの方から遅延評価の素晴らしさを説かれたが、現時点ではよくわかっていない。

++演算子と--演算子は破壊的演算子

前置と後置があり、前置は演算後の値が評価値となり、後置は演算前の値が評価値となる

 後置ばかり使うし、++と代入を一文で同時に行うことがほぼない気がする。紛らわしいからか

同値演算子、比較演算子の動作は一瞥してとりあえず先に進む。

論理演算子の評価値きもい。ブーリアン値じゃない値を吐くという点がきもい

ビット演算子、高校数学以外で使ったことない。

4章は以上。

一覧的、辞書的な章だったため内容的に突っ込む部分は少なかった。次章は変数とオブジェクトなのでいろいろありそう。

「パーフェクトJavaScript」メモ 3章 Javascriptの型

3章は「型」。jsでは値とオブジェクトには型はあるが変数には型はない。

基本型(オブジェクト型以外の型)のインスタンスを値と呼ぶ(本書では)

オブジェクト型のインスタンスをオブジェクトと呼ぶ(本書では) 

インスタンス」という語が整理できていなかった。ググったら「実体」だそうだ。「クラス」がシニフィアンで「インスタンス」がシニフィエというところか(遅れてきたニューアカか)。

にしても、インスタンスという言葉はもっと限定的な使われ方をしていたような気がするが果たして。

 

JAVAのように変数に型のある言語を静的型言語、jsのように変数に型のない言語を動的型言語と呼ぶ 

 変数の型をユーザーが定義するのがクラスベース、型を定義する構文がなく振る舞い方に型があるだけというのがプロトタイプベース 

 「プロトタイプ」は最初の模型というイメージか。この辺の用語はコミュニケーションのためということで覚えておきたい。

 

基本型と参照型の説明、詳細は二学期

 

jsの数値型は1種類。実行効率よりもプログラミングの手軽さを重視したため

 数値型がJAVAのように複数あるとなぜ実行効率が上がるのかは知らないまま、とりあえず生きてゆく

(小数の可能性も考えつつ操作するのと、整数だと割り切って操作するのでは後者の方が速い、という印象はある)

 

jsにおいて「型変換」は落とし穴になる

 とりあえず額面だけ覚えておく

 

jsにおいて、文字列リテラルを囲む"と'には違いはない

PHPでは違うな

 

s2 に s を代入した場合 s の変更が s2 に見えるかどうかというと、jsでは見えない

その方がありがたい。過去を追いかけなくてすむ

 

typeof(x) で返ってくる結果を typeof する― typeof(typeof(x)) ―と、文字列値が返ってくる 

ものには型があるんだ

 

js の文字列値は大小比較演算が可能

 知らなかった。。。でも実際は英単語の頭文字くらいにしか使えないだろうということで

 

3-3-4 文字列クラス(Stringクラス) 

この節はかなり感動的(1000文字足らずだが)。x.lengthで長さをはかれるのは x がStringオブジェクトだからか。前章でやったようにオブジェクトはプロパティの集合で、プロパティとしてlength情報を持っている。いっぽう文字列値にはlength情報はないため、暗黙に文字列値から文字列オブジェクトへの型変換が行われている。

 

==と===の違い

内容が同じであれば型が違ってもtrueになるのが==、型が違えばfalseになるのが===

この字面だけだと理解していたが、その周辺を知って理解が深まった感がある。

 

「メソッド呼び出し」という言葉があまりピンときていない。x.length とか x.toString() とかそういう操作っぽいことをするのをメソッド呼び出しということでいいか。

method って「方法」と訳しているから「操作」とはなんとなく思いにくい。でもまあプログラミングでは操作と思っておいた方がよいのだろう。

ともあれメソッドによる操作はオブジェクトに対して行うのであって、文字列値、数値に対して行うのではない(文字列値、数値に対してメソッド呼び出しをした場合、その場でオブジェクトに型変換される)。

 

new String([value]) の効果を「Stringインスタンスを生成」と言っている部分(p48)と「文字列オブジェクトを生成」と言っている部分(p45)がある。どっちも同じことか。「オブジェクトの中味を生成」と言うか「オブジェクトを生成」と言うかの違いかな。

 

(p48) String.prototypeオブジェクトのプロパティをまとめてくれているが、それがなんなのかわからない。

 

 Stringクラスには破壊的なメソッドがないが、Arrayクラスには破壊的なメソッドが多くある

うん。怖いのでいつも新しい変数を用意してしまう。駄目か。

 

数値リテラル .14 は 0.14 と等価数

むしろエラーを返してほしい気がする。

 

NaN は数値、数値オブジェクトになれないものを数値に型変換しようとした場合に成り果てるもの(Not a Number)。詳細は二学期

そうだったのか。「なんか知らんがエラー」と思っていた。平和ボケでしょう

 

>Number.MAX_VALUE.toString(16)
"fffffffffffff800000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000"

すべてがfにな らないのか。

 

Number.MIN_VALUE.toString(16)
"0.00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000004"

4ってなんだ

 

Number.POSITIVE_INFINITY という特別値もある

へえ。

 

NaN は NaN 同士の同値判定ですら偽になる

うわ。

 

そこでisNaNがある

よかった。

 

null値の本来的な意味は「何も参照していない」状態

null値の typeof演算の結果は "object"

 

undefined値はリテラル値ではなく定義済のグローバル変数

明示的に値を代入していない変数の初期値に過ぎない。

自分が要約した文字列をblockquoteで囲むのあまりよろしくない気がしてきた。けどラクなので続ける。

 

null値とundefine値を==で比較すると真になる

真になーるんS.O.S。真になーるんS.O.S。

 

jsでは暗黙の型変換に気をつけよう

はい

 

型変換のイディオムがいろいろある。

n+''  //数値から文字列値への型変換

+s //文字列力数値への型変換

!!s //なにかしらからブーリン型への型変換

 

・オブジェクトの中に「使えるメソッド」が既に入っている。(入ってないメソッドは使えない?)

「オブジェクトがメソッドを持つ」と言えるのは、そういうことでしょうか。すごい初歩的ではないでしょうかこれ。

 

3章終わり。

「パーフェクトJavaScript」メモ 1章,2章

「パーフェクトJavaScript」を読みながらメモ。中途半端なjs知識を確かなものにし、用語を整理してjsについて口頭でコミュニケーションができるようになるのが目標。

 

パーフェクトJavaScript (PERFECT SERIES 4)

パーフェクトJavaScript (PERFECT SERIES 4)

 

 

以下のメモだけ読んでも意味がない。書き方は随時工夫する。

-webブラウザごとの処理系があるのかー。Chromeならv8といったような

-レンダリングエンジンの違いは何の違いで生まれるのか。ブラウザじゃないのかな

--ブラウザとバージョン、あとデバイスみたいですね

-var で宣言しただけだとundefine値が入ってる。こいつについては後述らしい。

-動的型言語とはなにか、についても後述

-var による宣言なしで変数に値を代入できるが、最低だそうです。そいつは関数内で使ってもグローバル変数になってしまい周りに迷惑をかけるので最低だそうです

-const は後で値を変更できない、すなわち定数だけどエクマスクリプト準拠でない独自拡張だそうです。使うかどうかはあなた次第。

 

-関数という言葉。

-jsでは関数もオブジェクトである。関数でないオブジェクトもある。

-変数名と関数名は結局同じものである

-オブジェクトとは

--メモリ上の実体である

--状態を持つ

--プログラミングの操作対象となる

--jsでは、オブジェクトは名前と値のペアを指す。

---つまり、プロパティの集合とも言える(プロパティとは。)

 

-オブジェクトリテラル

--{プロパティ名:プロパティ値,プロパティ名:プロパティ値, ……}

-配列ですか。

-プロパティ名には識別子、文字列値、数値のどれかが必ずはいる。(識別子とは。)

-中括弧の直前のカンマは、エラーにならないが避けたほうがよい。

-エラーにならないからよくそのままになってるソースを見るのか。

-ドットで書いてたのは↓

オブジェクト名.プロパティ名

-プロパティ値にはオブジェクトを置くこともできるので、ドットは複数続いたりする

-ドットとブラケット[]演算子は同じことをしたいときに使える。すなわち、「場所」を指し示すのに使える。

-javascriptには言語仕様としてはクラスもメソッドもない。比喩として便宜上、それっぽい働きをするものをそう呼ぶことはある。というか、多い。多そう。

-コンストラクタという語の意味をよくわかってない

-(メモの問題点として、学んだことメモとつぶやきが一緒くたになっている)

-JAVAだとコレにあたる、という説明が多く出てくるが、JAVAはそのうちやりますので

-クラス機能の比喩、ちんぷんかんぷん。

 

-「配列はArrayクラスのインスタンスとして存在します」この一文を解読できない。

-プロパティ名のない(勝手に0,1,2...と振られる)オブジェクトを配列と呼んでるのかな〜と思っていました。オブジェクトとは別物みたいですね

-配列の要素には文字列や数値やオブジェクトや配列がなれる。

 

とりあえず2章まで終わってきりがいいので今日はここまで。

 

もうすぐ春ですね

pixiv blogがサービス終了するということではてなブログ開始。

書くことないかもしれませんが。