const a = []不是数组吗?! ð
#javascript #typescript #arrays #datastructures

介绍

当我在Frontend Masters上深入研究Primeagen's Algorithms课程时,我被一个启示所震惊:我们用来声明JavaScript中的阵列的熟悉的const a = [ ]语法实际上并不是传统意义上的阵列。这一发现令我感到惊讶,我感到渴望通过此博客与他人分享这种新发现的知识。

什么是数组?

数组是有序的值集合。每个值称为元素,每个元素在数组中具有数字位置,称为其索引。 JavaScript数组是未构图的:一个数组元素可能是任何类型的类型,并且同一数组的不同元素可能是不同类型的。数组元素甚至可能是对象或其他数组,它使您可以创建复杂的数据结构,例如对象和数组数组的数组。 JavaScript数组可能很稀疏:元素不需要连续索引,并且可能存在空白。每个JavaScript数组都有一个长度属性。对于Nonsparse数组,此属性指定数组中的元素数量。对于稀疏阵列,长度大于任何元素的最高索引。 JavaScript数组是JavaScript对象的一种专业形式,并且数组索引实际上只不过是恰好是整数的属性名称。 JavaScript数组是动态的:它们会根据需要生长或缩小,并且在您创建它时,无需声明数组的固定尺寸或在大小更改时重新分配它。

证据!

让我们为经验测试编写一些代码,并在引擎盖下找出什么类型的数据结构是 const a = []

P.S :我将使用TypeScript进行此证明,因此我有类型的安全性。

您可以在github repo中找到代码以供参考,也可以从下面复制并在您自己的计算机上进行处理

const a: number[] = [];

function time(fn: () => void): number {
    const now = Date.now();
    fn();
    return Date.now() - now;
}

function unshift(number: number) {
    for (let i = 0; i < number; ++i) {
        a.unshift(Math.random());
    }
}

function shift(number: number) {
    for (let i = 0; i < number; ++i) {
        a.shift();
    }
}

function push(number: number) {
    for (let i = 0; i < number; ++i) {
        a.push(Math.random());
    }
}

function pop(number: number) {
    for (let i = 0; i < number; ++i) {
        a.pop();
    }
}

function get(idx: number) {
    return function() {
        return a[idx];
    };
}

function push_arr(count: number) {
    return function() {
        push(count);
    };
}

function pop_arr(count: number) {
    return function() {
        pop(count);
    };
}

function unshift_arr(count: number) {
    return function() {
        unshift(count);
    };
}

function shift_arr(count: number) {
    return function() {
        shift(count);
    };
}

让我们总结:

  • 创建一个数组

  • 函数time:测量函数时间

    我们只想估计事物的速度或慢速。

  • 函数unshift:它将解开“ a” 一定次

    javaScript中的unshift表示添加到列表

  • 函数shift将移动“ a” 一定数量

    shift用于从列表的开头删除

  • 函数push将推动“ a” 一定数量的时间。

    推送方法用于在数组的末尾添加一个或多个元素

  • 函数pop将弹出“ a” 一定数量。

    pop方法用于从数组中删除最后一个元素并返回该元素。

  • 基于索引的功能get。以防万一它是引擎盖下的LinkedList,如果我们要逐步获得更大的索引,我们应该看到线性放缓。

  • 函数push_arrpop_arrshift_arrunshift_arr是高阶功能,将重复调用pushpopshiftshiftunshift函数。

  • 然后进行测试...

测试

现在我们将测试我们的功能,并尝试弄清楚结果指示

pro-tip :每当我们进行 performance 测试时,您应该使用阶梯梯子型方法,以便您可以看到它的成长方式,以便您可以运行线性回归。

const tests = [10, 100, 1000, 10000, 100000, 1_000_000, 10_000_000];
console.log("Testing get");
tests.forEach(t => {
    a.length = 0;
    push(t);
    console.log(t, time(get(t - 1)));
});

console.log("push");
tests.forEach(t => {
    a.length = 0;
    push(t);

    console.log(t, time(push_arr(1000)));
});

console.log("pop");
tests.forEach(t => {
    a.length = 0;
    push(t);

    console.log(t, time(pop_arr(1000)));
});

console.log("unshift");
tests.forEach(t => {
    a.length = 0;
    push(t);

    console.log(t, time(unshift_arr(1000)));
});

console.log("shift");
tests.forEach(t => {
    a.length = 0;
    push(t);

    console.log(t, time(shift_arr(1000)));
});

让我们总结:

  • 我们将使用10、100、100 .... 10000000元素进行测试。

  • 在第一次测试中,“测试获取”,我们将在值中转到push,并为最后一个元素做一个get

    此处的论文是,如果索引是线性的,我们应该看到速度放缓,因为数组变得更大

  • 在第二次测试中,“推”,我们将在生长到一定长度的t.

    后将其转到push

    如果按下是基于数组中的项目数,我们应该从理论上看到发生的放缓。因此,每个步骤都应该线性地变慢。

  • 相同的论文适用于“ pop”,“ shift”和“ unshift”测试。

结果

是时候运行我们的代码并检查结果锅的方式以及在谈论javaScript中的数组

中如何朝哪个方向发展。

因为这是打字稿,运行npx ts-node {file-name}.ts

测试获取

get

阵列的大小无关紧要。这是超级傻瓜。

测试推动

push

获得的情况相同,它'很快。

测试流行

pop

类似的结果与 get 推动,相当快。

测试解开和转移

unshift

在这里,我们观察到测试用例的速度非常慢,并且具有线性生长。

所以我们从这些结果中推断出什么:

results

  • 即时访问

  • 即时推动并在结尾处弹出

  • 线性转移和解散

因此,它是 arraylist

数组列表是类似于数组的数据结构,但是它具有动态大小,可让您更有效地添加和删除元素。数组列表通常用于编程语言中以存储和操纵项目集合。

结论

我们可以安全地得出JavaScript阵列是动态的,实际上是 ArrayLists 在引擎盖下。

学分

ThePrimeAgen


感谢您阅读此博客。我希望您发现这些信息有帮助,如果您喜欢它,请考虑与他人分享。

bye!