【Eloquent JavaScript和訳】 Chapter 4:データ構造: オブジェクトと配列

print(sum(range(1, 10)));

range についてはもう学びました。ここですることはこの行に sum 関数の働きをさせることです。この関数は数字配列を受け取り、それらの合計を返します。これを書いてください。簡単です。

function sum(numbers) {
var total = 0;
for (var i = 0; i < numbers.length; i++)
total += numbers[i];
return total;
}

print(sum(range(1, 10)));

前の章で関数 Math.max と Math.min が出てきました。これらが実際には Math という名前で保存したオブジェクトの属性 max と min であることにお気付きでしょう。これがオブジェクトのもう一つの役割、複数の関連値を保存する倉庫、です。

Math 内には実にたくさんの値があり、それらを全て地球環境に直接置いたら、それこそ汚染そのものです。名前の数が多ければ、その分だけ変数の値が書き換えられてしまう危険性も増えます。例えば max のような名前はどこでも使われる可能性があります。

既に使っている名前を変数に定義しようとすると、多くの言語はそれを阻止、または少なくとも警告します。しかし JavaScript は違います。

Math には数学関数や数学定数が一式揃っています。全ての三角関数 ― cos、sin、tan、acos、asin、atan ― があります。大文字 (PI や E) で書かれる π や e は定数を示す方法として一時流行しました。これまで我々も power 関数として使ってきた pow は、負数も分数指数も受け付けます。sqrt は平方根を求めるのに使います。max と min は 2 つの値の最大値または最小値を出します。round、floor、および ceil はそれぞれ数値を丸めて近似の整数、それよりも小さい整数、それよりも大きい整数を求めます。

Math には他にも多くの値がありますが、本ドキュメントは参考資料ではなく入門書です。参考資料とは何かを確かめる時に探すもので、それがその言語でどう呼ばれているかとかその働きを調べるものではありません。残念ながら、JavaScript には総合的かつ完全な参考資料は存在しません。これは現在の形が、その時々で色々な拡張を重ねて無秩序状態の過程で異なるブラウザーが生まれた結果ともいえます。「はじめに」で触れた ECMA 標準ドキュメントが基本言語のドキュメントとして信頼できるできるものですが、かなり読みづらいのが難点です。Math オブジェクトやその他の基本機能に関しては ここ をご覧ください。Sun のウェブサイト にまだ残っている Netscape の古いドキュメントも役に立ちますが、時代遅れで完全に正しいとは言えません。

Math オブジェクトで使えるものを探す方法を既に思いつかれたかもしれません:

for (var name in Math)
print(name);

悲しいかな、何も出てきません。次のようにしても同じです:

for (var name in ["Huey", "Dewey", "Loui"])
print(name);

0 や 1 や 2 は見えるのに、確実にそこにあるはずの length も push も join も見えません。明らかにオブジェクトの属性の中には隠されているものがあります。これには訳があります。全てのオブジェクトには、例えばオブジェクトを適当な文字列に変換する toString のように実行中はその属性を見たくないメソッドが 2~3 あります。本章で言えば、オブジェクトに保存した猫を検索中にそれらの属性を見たいとは思いません。

Math の属性が何故隠されているのか、私には分かりません。誰かオブジェクトを謎めいたものにしたかったのかもしれません。

プログラムがオブジェクトに追加する属性は全て可視的で、それを隠すことはできません。8 章 で見るように、for/in ループで属性が見えないようにしてメソッドをオブジェクトに追加できたら良いのですが、残念です。

属性の中には読み取り専用のものがあり、値は入手できますが変更することはできません。例えば、文字列値の属性は全て読み取り専用です。

他の属性は '表示 (watch)' することができます。属性を変えれば 結果 も変わります。例えば、配列の長さを短く指定すれば、余分なエレメントは切り捨てられます:

var array = ["Heaven", "Earth", "Man"];
array.length = 2;
show(array);

ブラウザーによってはオブジェクトに watch メソッドがあり、これを使って自身の属性に watcher を追加することができます。Internet Explorer はこれをサポートしていないため、書いているプログラムが全ての '有名な' ブラウザーで実行されなければならない場合はあまり役に立ちません。

var winston = {mind: "compliant"};
function watcher(propertyName, from, to) {
if (to == "compliant")
print("Doubleplusgood.");
else
print("Transmitting information to Thought Police...");
}
winston.watch("mind", watcher);

winston.mind = "rebellious";

翻訳元