12

私は、Javascript にはプリミティブ型と参照型があるという前提で生きてきました。日常的に、このような影響を受けたことは一度もありませんが、より多くの JS を使い始めたばかりで、自分の「考え方」を更新したいと考えていました。言い換えれば、次の式が 68 を返すことに 20 ドルを賭けたはずです。

var my_obj = {};
var tmp_obj = {};

tmp_obj.my_int = 38;
my_obj.tmp_val = tmp_obj.my_int;
tmp_obj.my_int = 68;

alert('68 means reference, 38 means primitve: ' + my_obj.tmp_val);

しかし、それは 38 を返します。

ここに画像の説明を入力

参照型のコンテキストに存在する場合でも、数値のすべてのインスタンスはプリミティブ型ですか? y の場合、私は本当に驚いて、その奇妙な動作を見つけます (そして 20 ドルかかるでしょう)。それとも、私の例は私が考えていることを示していませんか?

thx事前に

更新 #1

うわー、すべての答えにthx。これは、理解するのに非常に役立つわずかな変更です。

var my_obj={};
var tmp_obj={};
var my_obj_2=tmp_obj;
tmp_obj.my_int=38;
my_obj.tmp_val=tmp_obj.my_int;
tmp_obj.my_int=68
alert('68 means reference, 38 means primitve: ' + my_obj.tmp_val);   // 38
alert('68 means reference, 38 means primitve: ' + my_obj_2.my_int);  // 68
my_obj_2.my_int=78;
alert(tmp_obj.my_int); // tmp_obj is now 78 ie two way
4

5 に答える 5

7

あなたが持っていた場合、あなたの例は期待どおりに機能します

     my_obj = tmp_obj;

次に、オブジェクトが 1 つしかないため、すべてのプロパティが同じ参照を指します。

しかし、あなたが書くとき

     my_obj.tmp_val = tmp_obj.my_int;

次にmy_obj.tmp_val、格納されている値を取得しますtmp_obj.my_intが、2 つのオブジェクト間に新しい参照は作成されません。

于 2013-01-21T16:55:57.067 に答える
6

Java のような構文を使用する場合、値が変更された整数オブジェクトがある場合、コードがこのように動作することを期待していたようです。

tmp_obj.my_int = new Integer(38);
my_obj.tmp_val = tmp_obj.my_int;
tmp_obj.my_int.setValue(68);

出力されないため68、整数は参照型ではなくプリミティブ型である必要があると結論付けます。ただし、必ずしもそうであるとは限りません。この別の解釈を考えてみましょう:

tmp_obj.my_int = new Integer(38);
my_obj.tmp_val = tmp_obj.my_int;
tmp_obj.my_int = new Integer(68);

ここで、整数は参照型ですが、整数への割り当ては参照の上書きを意味するためmy_obj.tmp_val、値は引き続き含まれます。38

整数は不変オブジェクトと考えることができます。JavaScript は、すべてがオブジェクトであるという統一されたビューを提示するのに非常に優れているため、「整数はプリミティブ型」よりも結果をより適切に解釈できます。

于 2013-01-21T16:56:23.077 に答える
4

はい、数値や文字列などの値はプリミティブ値のように機能します。それらは不変です。変数に新しい値を割り当てると、古い値が置き換えられますが、そこにある値は変更されません。

例:

var x = 42;
var y = x; // y == 42
x = 1337; // this puts a new value in x, it doesn't change 42 to be 1337
alert(y); // it's still 42

同じことが文字列に対しても機能します。

var x = "42";
var y = x; // y == "42"
x = "1337"; // this puts a new string in x, it doesn't change "42" to be "1337"
alert(y); // it's still "42"

また、オブジェクトのプロパティを使用する場合。

var o = {};
o.x = 42;
o.y = o.x; // o.y == 42
o.x = 1337; // this puts a new value in o.x, it doesn't change 42 to be 1337
alert(o.y); // it's still 42

値がどのように機能するかは、通常の変数に格納されているか、オブジェクトのプロパティに格納されているかではなく、その型にのみ依存します。

文字列が内部でオブジェクトとして実装されていても、それは不変であり、値として機能します。文字列をコピーすると、オブジェクトへの参照がコピーされる場合がありますが、文字列値自体は何も変更できないため、別のコピーを取得することになります。

于 2013-01-21T17:00:25.130 に答える
3

私は、Javascript にはプリミティブ型と参照型があるという前提で生きてきました。

それは本当だ。ただし、参照値はオブジェクトのみです。プリミティブ値は変更できません。

参照型のコンテキストに存在する場合でも、数値のすべてのインスタンスはプリミティブ型ですか?

はい。それらのコンテキストは関係ありません。

于 2013-01-21T16:56:10.543 に答える
2

ここで理解すべき重要なことが2つあると思います。

  1. プリミティブ値は参照ではありません
  2. JavaScript参照を割り当てることはできず、コピーするだけです。

最初のポイントを示すためにこのコードを検討します。

var a = 10,
    b = a,
    c = {foo : 20}
    d = c.foo;

b = 20;
d = 30;
a;     // 10;
c.foo; // 20;

したがって、参照ではなくプリミティブ値を保持する「スロット」(変数またはプロパティ)があります。これらのスロットの1つで値を変更しても、他のスロットには影響しません。

2番目のポイントを考慮して:

var a = {foo: true},
    b = a;
b.foo; // true
b.foo = false;
a.foo; // false;
b = {bar: false};
a;     // {foo: false}

変数aにはオブジェクトが含まれており、b最初は同じオブジェクトへの参照です。に割り当てると、とはまったく同じオブジェクトを指しているため、に影響しますb.foo。ただし、これらの参照は、特定のスロットに格納されている他の値とまったく同じです。スロットに何か他のものを割り当てると、参照は別の値に置き換えられます。したがって、に割り当てても影響はありません。ababa

于 2013-01-21T17:04:10.313 に答える