JavaScript中关联数组的[]和{}之间的差异

用户名

现在实现一个简单的数据库。

我认为,这个问题的重复标签判断不好。链接的问题对我的要求没有任何帮助。

用户ID引用了用户数据,我有2个选项可以做到以下几点:DB1DB2

var DB1 = {
    user: {}
};
var DB2 = {
    user: []
};

DB1.user['001'] = {
    email: '[email protected]',
    name: 'ken'
};
DB2.user['001'] = {
    email: '[email protected]',
    name: 'ken'
};

console.log(DB1.user['001']);
console.log(DB2.user['001']);

DB1和DB2的行为完全以预期的方式相同,至少在我看来是如此。

有什么区别吗?只是表达{}或[]的一种方法吗?

如果不同,哪个更有效?

感谢您的想法。

更新:

非常感谢所有为我提供详细解答的人。

在这种情况下,我大概可以理解,用于关联方式的数组[]实际上是一个对象。

在这种情况下,它的行为相同(因为对象不是数组),我知道。

因此,在这种情况下,我想知道的是[]和{}的区别。

更重要的是,在这种情况下,如果不仅是表达式,如何不同以及哪种效率更高,那就是我想知道的。谢谢。

UPDATE2:

好的,这并不是很多人认为的那么明显。我编写了一个测试代码,如下所示:

var DB1 = {
    user:
    {}
};
var DB2 = {
    user: []
};
var DB3 = {
    user: []
};

for (var i = 0; i < 100000; i++)
{
    var id = ('0000' + i)
        .slice(-5);

    DB1.user[id] = {
        email: '[email protected]',
        name: 'ken'
    };

    DB2.user[id] = {
        email: '[email protected]',
        name: 'ken'
    };

    DB3.user[i] = {
        email: '[email protected]',
        name: 'ken'
    };

}
//confirm the value just in case
console.log(DB1.user['00000']);
console.log(DB1.user['00001']);
console.log(DB1.user['99999']);
console.log(DB1.user['100000']);

for (var t = 0; t < 10; t++)
{
    console.log('-----------test ' + t);
    console.time('DB1');
    for (var i = 0; i < 100000; i++)
    {
        var id = ('0000' + i)
            .slice(-5);

        var data = DB1.user[id];
    }
    console.timeEnd('DB1');

    console.time('DB2');
    for (var i = 0; i < 100000; i++)
    {
        var id = ('0000' + i)
            .slice(-5);

        var data = DB2.user[id];
    }
    console.timeEnd('DB2');


    console.time('DB3');
    for (var i = 0; i < 100000; i++)
    {
        var id = ('0000' + i)
            .slice(-5);

        var id1 = id * 1;
        var data = DB3.user[id1];
    }
    console.timeEnd('DB3');
}

结果:

{ email: '[email protected]', name: 'ken' }
{ email: '[email protected]', name: 'ken' }
{ email: '[email protected]', name: 'ken' }
undefined

-----------test 0
DB1: 46ms
DB2: 68ms
DB3: 28ms
-----------test 1
DB1: 39ms
DB2: 33ms
DB3: 26ms
-----------test 2
DB1: 32ms
DB2: 39ms
DB3: 25ms
-----------test 3
DB1: 57ms
DB2: 33ms
DB3: 27ms
-----------test 4
DB1: 39ms
DB2: 35ms
DB3: 27ms
-----------test 5
DB1: 39ms
DB2: 32ms
DB3: 27ms
-----------test 6
DB1: 33ms
DB2: 36ms
DB3: 26ms
-----------test 7
DB1: 39ms
DB2: 41ms
DB3: 40ms
-----------test 8
DB1: 32ms
DB2: 32ms
DB3: 28ms
-----------test 9
DB1: 36ms
DB2: 31ms
DB3: 28ms

对于100000条记录,数组DB稍微快一点,但是我想我将使用关联数组样式的Object DB。

TJ人群

DB1和DB2的行为完全以预期的方式相同,至少在我看来是如此。

不完全的。[]创建一个数组,{}创建一个对象。在JavaScript中,标准数组根本不是真正的数组,它们只是具有某些特殊行为的对象。您可以将属性添加到不是数组条目的那些对象,就像可以添加任何其他对象一样。在你的榜样,你不使用数组作为数组,这样既工作,但如果你使用数组作为数组(使用数组索引,lengthpushsplice,等),只有[]版本将仅给出工作你一个数组。

需要阵列功能时,请使用阵列。仅在将名称映射到值时使用一个对象。如果使用数组,请确保使用真正的数组索引,而不要使用非索引属性名称'001'(有关以下内容的详细信息。)

这是一个不使用数组作为数组的示例:

DB1.user['001'] = ...;

那不会创建一个数组入口。证明:

var a = [];
a['001'] = "foo";
console.log(a.length); // 0

它在名称为的对象上创建一个属性"001",但该属性不是数组项。相反:

a[1] = "foo";

要么

a['1'] = "foo";

...创建一个数组条目:

var a = [];
a[1] = "foo";
console.log(a.length); // 2 (see below)

为什么会有所不同?同样,标准数组只是具有特殊行为的对象。特殊行为的关键点之一与一属性名称有关,特别是那些都是普通数字形式的数字(没有前导零)(即使我们像数字一样工作,它们仍然是字符串)。名称为标准数字形式(且在范围内,允许为0到2 32 -2,包括端值)的属性是数组条目。


我一直说“标准数组”是因为JavaScript正在获取类型数组(实际上,大多数引擎中已经存在它们):

var a = new Int32Array(10);

类型化数组是实际数组,完全不同于[]“数组”。


旁注:为什么这里length 2个

var a = [];
a[1] = "foo";
console.log(a.length); // 2

因为JavaScript数组本质上是稀疏的,所以我所谈论的特殊行为之一是,当您向符合数组条目定义的数组添加属性时length,其值将设置为大于最高值的值。编号的数组条目。因此,即使我们的a数组只有一个条目,它length也是2。


补充说明:在JavaScript中,对象不称为“关联数组”,这主要是PHP术语,表示它具有非常特殊的数据结构,该结构是有序的名称/值映射。在JavaScript中,我们称它们为“对象”(主要),有时也称为“地图”或“词典”。与PHP的关联数组不同,它们是无序的。


更重要的是,在这种情况下,如果不仅是表达式,如何不同以及哪种效率更高,那就是我想知道的。

由于您未将数组用作数组,因此我希望对象版本会稍微提高效率,因为引擎最初会根据您将数组用作数组来尝试进行优化,然后再回退到对象行为当您做诸如'001'财产名称之类的事情时因此,可能从一开始就使用对象。

但是总的来说,JavaScript的“效率”是一个非常困难的话题。在一个引擎上有效的效率在其他引擎上无效。即使您不相信过早的优化在其他领域也浪费时间,但JavaScript确实如此显然,不要做任何愚蠢的事情,但是通常,请等到出现性能问题,然后在出现该问题的平台上解决该问题(然后测试您支持的其他平台,以确保您没有引入新问题。那里)。

本文收集自互联网,转载请注明来源。

如有侵权,请联系[email protected] 删除。

编辑于
0

我来说两句

0条评论
登录后参与评论

相关文章