'var { ... } = ...' 语句中的大括号有什么作用?

不确定这是否是Mozilla特定的JS语法,但我经常发现变量以这种方式声明,例如,在附加SDK文档中

var { Hotkey } = require("sdk/hotkeys");

和在各种铬 Javascript ( 语句被用于代替 ),letvar

let { classes: Cc, interfaces: Ci, results: Cr, utils: Cu }  = Components;

我发现它非常令人困惑,但我无法找到有关这两种语法的任何文档,即使在MDN上也是如此。


答案 1

你所看到的是一个解构任务。这是一种模式匹配的形式,就像在Haskell中一样。

使用解构赋值,您可以从对象和数组中提取值,并使用对象和数组文本语法将它们分配给新声明的变量。这使得代码更加简洁。

例如:

var ascii = {
    a: 97,
    b: 98,
    c: 99
};

var {a, b, c} = ascii;

上述代码等效于:

var ascii = {
    a: 97,
    b: 98,
    c: 99
};

var a = ascii.a;
var b = ascii.b;
var c = ascii.c;

对于数组也是如此:

var ascii = [97, 98, 99];

var [a, b, c] = ascii;

这等效于:

var ascii = [97, 98, 99];

var a = ascii[0];
var b = ascii[1];
var c = ascii[2];

还可以提取和重命名对象属性,如下所示:

var ascii = {
    a: 97,
    b: 98,
    c: 99
};

var {a: A, b: B, c: C} = ascii;

这等效于:

var ascii = {
    a: 97,
    b: 98,
    c: 99
};

var A = ascii.a;
var B = ascii.b;
var C = ascii.c;

这就是它的全部内容。


答案 2

它们都是 JavaScript 1.7 的功能。第一个是块级变量

let允许您声明变量,将其范围限制为使用它的块、语句或表达式。这与关键字不同,关键字全局定义变量,或局部定义整个函数的变量,而不考虑块作用域。var

第二个叫做解构

通过解构赋值,可以使用镜像数组和对象文本构造的语法从数组或对象中提取数据。
...
使用解构赋值可以执行的一个特别有用的操作是在单个语句中读取整个结构,尽管您可以使用它们执行许多有趣的操作,如以下示例部分所示。

对于那些熟悉Python的人来说,它类似于以下语法:

>>> a, (b, c) = (1, (2, 3))
>>> a, b, c
(1, 2, 3)

第一个代码块是以下代码的简写:

var {Hotkey: Hotkey} = require("sdk/hotkeys");
// Or
var Hotkey = require("sdk/hotkeys").Hotkey;

您可以将第二个代码块重写为:

let Cc = Components.classes;
let Ci = Components.interfaces;
let Cr = Components.results;
let Cu = Components.utils;