JavaScript属性访问:点符号与括号?

Mar*_*ouf 380 javascript syntax

除了显而易见的事实,即第一种形式可以使用变量而不仅仅是字符串文字,是否有任何理由使用其中一种,如果是这样,在哪种情况下呢?

在代码中:

// Given:
var foo = {'bar': 'baz'};

// Then
var x = foo['bar'];

// vs. 
var x = foo.bar;
Run Code Online (Sandbox Code Playgroud)

上下文:我编写了一个生成这些表达式的代码生成器,我想知道哪个更好.

Aro*_*eel 412

(来自这里.)

方括号表示法允许使用不能与点表示法一起使用的字符:

var foo = myForm.foo[]; // incorrect syntax
var foo = myForm["foo[]"]; // correct syntax
Run Code Online (Sandbox Code Playgroud)

包括非ASCII(UTF-8)字符,如myForm["?"](更多示例)中所示.

其次,在处理以可预测的方式变化的属性名称时,方括号表示法很有用:

for (var i = 0; i < 10; i++) {
  someFunction(myForm["myControlNumber" + i]);
}
Run Code Online (Sandbox Code Playgroud)

围捕:

  • 点符号编写速度更快,读取更清晰.
  • 方括号表示法允许访问包含特殊字符的属性以及使用变量选择属性

另一个不能与点表示法一起使用的字符示例是属性名称,它们本身包含一个点.

例如,json响应可以包含一个名为的属性bar.Baz.

var foo = myResponse.bar.Baz; // incorrect syntax
var foo = myResponse["bar.Baz"]; // correct syntax
Run Code Online (Sandbox Code Playgroud)

  • 没有必要重新发明轮子,是吗?引用它作为参考. (60认同)
  • 代码示例和摘要的措辞看起来非常熟悉.http://www.dev-archive.net/articles/js-dot-notation/ (44认同)
  • 点符号更快(至少对我来说)测试你的浏览器http://jsperf.com/dot-notation-vs-bracket-notation/2 (11认同)
  • 但我想知道,一个比另一个快吗? (4认同)
  • 在我的机器支架表示法中的镀铬44更快 (3认同)
  • @chenghuayang当你想访问一个对象的属性时,你的密钥存储在一个变量中,你不能用点表示法. (2认同)

nai*_*vin 103

括号表示法允许您通过存储在变量中的名称访问属性:

var obj = { "abc" : "hello" };
var x = "abc";
var y = obj[x];
console.log(y); //output - hello
Run Code Online (Sandbox Code Playgroud)

obj.x 在这种情况下不会起作用.


Bel*_*mir 13

foo.barfoo["bar"]访问 foo 上的属性,但不一定是相同的属性。区别在于如何bar解释。使用点时,点后面的单词是属性的字面名称。使用方括号时,将计算括号之间的表达式以获取属性名称。而foo.bar获取名为 的值的\n属性\xe2\x80\x9cbar\xe2\x80\x9dfoo["bar"]尝试计算表达式"bar"并使用转换为字符串的结果作为属性名称

\n

点表示法\xe2\x80\x99s 限制

\n

如果我们采用这个对象:

\n
const obj = {\n  123: 'digit',\n  123name: 'start with digit',\n  name123: 'does not start with digit',\n  $name: '$ sign',\n  name-123: 'hyphen',\n  NAME: 'upper case',\n  name: 'lower case'\n};\n
Run Code Online (Sandbox Code Playgroud)\n

使用点表示法访问其专有内容

\n
obj.123;      // \xe2\x9d\x8c SyntaxError\nobj.123name;  // \xe2\x9d\x8c SyntaxError\nobj.name123;  // \xe2\x9c\x85 'does not start with digit'\nobj.$name;    // \xe2\x9c\x85  '$ sign'\nobj.name-123;  // \xe2\x9d\x8c SyntaxError\nobj.'name-123';// \xe2\x9d\x8c SyntaxError\nobj.NAME; // \xe2\x9c\x85 'upper case'\nobj.name; // \xe2\x9c\x85 'lower case'\n
Run Code Online (Sandbox Code Playgroud)\n

但这对于括号表示法来说都不是问题:

\n
obj['123'];     // \xe2\x9c\x85 'digit'\nobj['123name']; // \xe2\x9c\x85 'start with digit'\nobj['name123']; // \xe2\x9c\x85 'does not start with digit'\nobj['$name'];   // \xe2\x9c\x85 '$ sign'\nobj['name-123']; // \xe2\x9c\x85 'does not start with digit'\nobj['NAME']; // \xe2\x9c\x85 'upper case'\nobj['name']; // \xe2\x9c\x85 'lower case'\n
Run Code Online (Sandbox Code Playgroud)\n

使用变量访问变量:

\n
const variable = 'name';\nconst obj = {\n  name: 'value'\n};\n// Bracket Notation\nobj[variable]; // \xe2\x9c\x85 'value'\n// Dot Notation\nobj.variable; // undefined\n
Run Code Online (Sandbox Code Playgroud)\n


Ben*_*ier 11

点符号不适用于Internet Explorer 8中的某些关键字(如newclass).

我有这个代码:

//app.users is a hash
app.users.new = {
  // some code
}
Run Code Online (Sandbox Code Playgroud)

这触发了可怕的"预期的标识符"(至少在Windows XP上的IE8上,我没有尝试过其他环境).对此的简单修复是切换到括号表示法:

app.users['new'] = {
  // some code
}
Run Code Online (Sandbox Code Playgroud)


Sag*_*jal 10

在JavaScript中访问属性的两种最常用方法是使用点和方括号.两者都value.x and value[x]在值上访问属性,但不一定是相同的属性.不同之处在于如何解释x.使用点时,点后面的部分必须是有效的变量名,并直接命名该属性.使用方括号时,将计算括号之间的表达式以获取属性名称.value.x获取名为"x"的值的属性,而value [x]尝试计算表达式x并使用结果作为属性名称.

所以,如果你知道你感兴趣的房产被称为"长度",你说value.length.如果你想提取由变量中保存的值命名的属性i,你说value[i].并且因为属性名称可以是任何字符串,如果要访问名为“2”或的属性“John Doe”,则必须使用方括号:value[2] or value["John Doe"].即使您事先知道属性的确切名称也是如此,因为它们都不“2” nor “John Doe”是有效的变量名,因此无法通过点表示法访问.

在阵列的情况下

数组中的元素存储在属性中.因为这些属性的名称是数字,我们经常需要从变量中获取它们的名称,所以我们必须使用括号语法来访问它们.数组的length属性告诉我们它包含多少个元素.这个属性名是一个有效的变量名,我们事先知道它的名字,所以为了找到一个数组的长度,你通常会写,array.length因为它比写更容易array["length"].

  • 这个答案特别有价值,因为它解释了两种符号之间的区别。 (2认同)

小智 8

使用这些符号时要小心:例如.如果我们想要访问窗口父级中存在的函数.在IE中:

window['parent']['func']
Run Code Online (Sandbox Code Playgroud)

不等于

window.['parent.func']
Run Code Online (Sandbox Code Playgroud)

我们可以使用:

window['parent']['func'] 
Run Code Online (Sandbox Code Playgroud)

要么

window.parent.func 
Run Code Online (Sandbox Code Playgroud)

访问它


CdB*_*CdB 6

一般来说,他们做同样的工作.
尽管如此,括号表示法让你有机会做一些你用点符号做不到的东西,比如

var x = elem["foo[]"]; // can't do elem.foo[];
Run Code Online (Sandbox Code Playgroud)

这可以扩展到包含特殊字符的任何属性.


Har*_*hid 6

您必须在以下情况下使用方括号表示法 -

  1. 属性名称是数字。

    var ob = {
      1: 'One',
      7 : 'Seven'
    }
    ob.7  // SyntaxError
    ob[7] // "Seven"
    
    Run Code Online (Sandbox Code Playgroud)
  2. 属性名称具有特殊字符。

    var ob = {
      'This is one': 1,
      'This is seven': 7,
    }  
    ob.'This is one'  // SyntaxError
    ob['This is one'] // 1
    
    Run Code Online (Sandbox Code Playgroud)
  3. 属性名称分配给一个变量,您希望通过该变量访问属性值。

    var ob = {
      'One': 1,
      'Seven': 7,
    }
    
    var _Seven = 'Seven';
    ob._Seven  // undefined
    ob[_Seven] // 7
    
    Run Code Online (Sandbox Code Playgroud)


Álv*_*lez 5

如果属性名称具有特殊字符,则需要使用括号:

var foo = {
    "Hello, world!": true,
}
foo["Hello, world!"] = false;
Run Code Online (Sandbox Code Playgroud)

除此之外,我想这只是一个品味问题.恕我直言,点符号更短,它更明显,它是一个属性而不是数组元素(虽然当然JavaScript无论如何都没有关联数组).


Lev*_*ich 5

括号表示法可以使用变量,因此它在点表示法不起作用的两种情况下很有用:

1) 当属性名称是动态确定的时(直到运行时才知道确切的名称)。

2) 当使用 for..in 循环遍历对象的所有属性时。

来源:https ://developer.mozilla.org/en-US/docs/Web/JavaScript/Guide/Working_with_Objects