2012-08-15 71 views
1

這個問題實際上是另一個question的結果,爲此我做了一些實驗,結果讓我更加困惑。我期待着解釋內部實際發生的答案。JavaScript變量賦值令人驚訝

我曾嘗試是,

我一直以此爲基礎估計,因爲我得到了一些明確的解釋 here

var a = []; 
a['a1'] = []; 
a['a2'] = []; 

console.log(a); // [] 
console.log(a['a1']); // [] 
console.log(a['a2']); // [] 

TEST 1

這讓我感到困惑很多,因爲它打印b[0]a,並且可以訪問length財產,我以爲var b可以被視爲一個字符數組,因此我試圖分配另一個值,但最終沒有成功。從基本假設,如果這個可以被視爲一個char數組(更一般地作爲一個數組),分配應該是成功的。它打破了基本假設。

var b = 'abcd'; 
b['b1'] = []; 

console.log(b); // abcd 
console.log(b.length); // 4 
console.log(b['b1']); // undefined 

TEST 2

但是,如果我創建這樣的分配是發生了,

var bb = ['a', 'b', 'c', 'd']; 
bb[4] = []; 

console.log(bb); // ["a", "b", "c", "d", []] 
console.log(bb.length); // 4 
console.log(bb[0]); // a 
console.log(bb[4]); // [] 

由此,我認爲,b[4] = [];可能會成功,但

var b = 'abcd'; 
b[4] = []; 

console.log(b); // abcd 
console.log(b.length); // 4 
console.log(b[4]); // undefined 

我的問題是,爲什麼這些賦值的行爲不同,而變量共享一些共同的功能?

這裏是demo

誰能請給我什麼實際發生的內部一個明確的解釋嗎?

額外測試

那麼,如果我用數值轉讓嘗試,它的行爲完全不同的形成這兩個。

var c = 1234; 
c[4] = []; 

console.log(c); //1234 
console.log(c.length); // undefined 
console.log(c[0]); //undefined 
console.log(c[4]); //undefined 
+0

你假定一個字符串是一個字符數組。這不是,所以你從這個假設中得到的任何東西都不會起作用。 – JJJ 2012-08-15 16:26:17

+0

@Juhana完全沒有,假設,可以被視爲一個字符數組,因爲結果混淆。 – 2012-08-15 17:23:21

回答

0

推理

你的 「基礎估計」 工程,因爲a是一個數組。 「測試2」是您編寫的使用數組的唯一其他測試用例,這就是爲什麼這是唯一可行的其他測試用例。

你似乎認爲提供一個方括號表示法並且有一個length方法表明一個對象是一個數組。這不是真的。要測試一個對象是否是一個數組,你可以使用JavaScript的instanceof方法,如下所示:

var a = []; 
var b = 'abcd'; 
var bb = ['a', 'b', 'c', 'd']; 
var c = 1234; 

a instanceof Array // => true 
b instanceof Array // => false 
bb instanceof Array // => true 
c instanceof Array // => false 

注意,這裏instanceof Array回報true是因爲你預期的行爲是對的,因爲你正在嘗試的案件執行數組操作。


爲什麼 「測試1」 失敗

對於 「測試1」,字符串方括號標記進行串類的charAt功能。給定b = 'abcd',執行b[0]與執行b.charAt(0)相同。它是隻讀的,只是返回該索引處的字符,即「a」。

查看the Mozilla Developer Network documentation for Strings瞭解更多詳情。


爲什麼「額外測試」失敗

爲貴「的額外的測試」,整不提供方括號標記或長度的方法,因此,所有這些調用的失敗。

+0

我接受推理,但是我想知道的是,如果'b'或'c'不是一種數組,那麼賦值如何成功,甚至不會拋出任何異常。 – 2012-08-15 17:16:51

+0

他們沒有失敗。雖然文字不提供屬性,但是自動實例化的對象也可以。嘗試'alert(42 [「構造函數」])'。這些調用並沒有失敗,只是'Number'實例在數字屬性上沒有任何有意義的數據。另外,方括號用於索引任何對象,它不是數組的唯一。 – 2012-08-16 09:01:17

1

測試1:b內部是一個字符串,而不是一個數組,這樣你就不能分配在b位置的東西。

測試2:偏離它的工作原理,因爲現在bb是一個數組。

我的問題是,爲什麼這些賦值行爲不同,而 變量共享一些共同的功能?

因爲它們的類型不同。

測試3: c是一個數字,而不是一個數組。

也許你有一些C背景,其中字符串是由空字符(\0)終止的字符數組。在JavaScript中,字符串是內置的int類型,它們的行爲與數組不同。喬納森說,[]運營商只是一個方便的訪問特定的字符。這裏有一些鏈接,來看看:

+0

在第二行中有小錯字'b'應該是'bb' – 2012-08-16 03:10:14

+0

@sogeek:固定的。謝謝! – davidbuzatto 2012-08-16 13:21:11

0

我想我不跟隨你的問題是什麼。 Javascript以不同的方式處理字符串,數組和整數。你不應該指望他們以同樣的方式行事。也沒有像JavaScript中的關聯數組到第一個例子可以工作的地方。 a['a1']符號類型實際上只是訪問對象屬性的一種替代方法,在字符串的上下文中沒有意義。

1

當您訪問除[]以外的任何對象時,會爲您提供一個以正確原型實例化的臨時對象(如StringNumber)。您可以像使用其他任何軟件一樣讀取和寫入此對象的屬性 - 例如,嘗試使用alert(3["constructor"])。然而,因爲這個對象在任何地方都沒有被引用,所以在你完成索引之後它會立即進入垃圾,並且當你下次嘗試讀取剛設置的屬性時,實際上是在訪問新的臨時對象上的屬性,自然是空的。

相關問題