简体   繁体   English

javascript数组填充异常

[英]javascript array filled strangely

I am writing an app in angular, and creating an array of custom services called Workbooks that each have an array of custom services called Views. 我正在用角度编写一个应用程序,并创建了一个名为Workbooks的自定义服务数组,每个自定义服务都有一个名为Views的自定义服务数组。 I fill the array with a simple for loop, but for some reason this is producing unexpected results: 我用一个简单的for循环填充数组,但是由于某些原因,这会产生意外的结果:

After the first iteration, there is one workbook in the array: Workbook 1 第一次迭代后,数组中有一个工作簿: Workbook 1

After the second, two workbooks titled workbook 2 : Workbook 2 Workbook 2 在第二个之后,有两个名为工作 Workbook 2 Workbook 2 簿Workbook 2 Workbook 2

After the third: Workbook 3 Workbook 3 Workbook 3 第三之后: Workbook 3 Workbook 3 Workbook 3

And so on. 等等。 How could this be happening? 这怎么可能发生? Here is a simplified version of the code that creates the workbooks and adds them to the array: 这是创建工作簿并将其添加到数组的代码的简化版本:

for (var i = 0; i < 3; i++) {
    var workbook = Workbook;
    workbook.setTitle("workbook " + (i + 1));
    for (var j = 0; j <2; j++ ) {
        var view = View;
        view.setTitle("view " + (j + 1));
        workbook.addView(view);
    }

    workbooks[i] = workbook;

    //this next for loop can be used to print the array as described    
    for (var k = 0; k < workbooks.length; k++) {
        console.log(workbooks[k].getTitle());
    }
}

return workbooks;

How could this happen? 怎么会这样 The ith workbook is assigned a title and then assigned to the ith spot in the array. 第一个工作簿被分配一个标题,然后分配给数组中的第一个点。 When i is 2, how can a workbook called Workbook 3 be assigned to the 0th and 1st spot in the array as well as the 2nd? i为2时,如何将名为Workbook 3的工作Workbook 3分配给数组中的第0和第1点以及第2点?

For reference, here is a plunker to the relevant code from the app. 作为参考,以下是该应用程序相关代码的小插曲 Thanks! 谢谢!

You aren't assigning the ith workbook to every spot in the array, you are assigning the SAME workbook to each of them, and then updating the title. 您没有将ith工作簿分配给数组中的每个位置,而是将SAME工作簿分配给了每个工作簿,然后更新了标题。 You need to make 你需要做

var workbook = Workbook;

into this 进入这个

var workbook = new Workbook;

Well, first problem: 好,第一个问题:

for (var i = 0; i < 3; i++) {
var workbook = Workbook;
workbook.setTitle("workbook " + (i + 1));

Each time through this loop, you are re-creating the variable 'workbook', and assigning it the name 'workbook X'. 每次通过此循环,您都将重新创建变量“工作簿”,并将其命名为“工作簿X”。

But it is looking like you aren't creating a NEW workbook each time, instead you are reusing the same reference, so each workbook ends up being simply a reference to the same object. 但是看起来您并不是每次都在创建NEW工作簿,而是您在重复使用相同的引用,因此每个工作簿最终都只是对同一对象的引用。

When you step through the loop the next time, you are simply reassigning the title of this reference, and both of them are updating. 下次当您遍历循环时,您只是在重新分配该引用的标题,并且两者都在更新。

Try this and see how it responds. 试试这个,看看它如何响应。

var workbook; // Just cleaner, avoids re-declaring the variable
for (var i = 0; i < 3; i++) {
    workbook = new Workbook; // avoids re-referencing the same Workbook
    workbook.setTitle("workbook " + (i + 1));
    for (var j = 0; j <2; j++ ) {
        var view = View;
        view.setTitle("view " + (j + 1));
        workbook.addView(view);
    }

    workbooks[i] = workbook;

    //this next for loop can be used to print the array as described    
    for (var k = 0; k < workbooks.length; k++) {
        console.log(workbooks[k].getTitle());
    }
}

return workbooks;

You need to return new object per factory call in your implementation of factory. 在工厂的实现中,您需要在每次工厂调用时返回新对象。

GATapp.factory('Workbook', function () { 
    return function () {
        var title;
        var views = [];
        this.getTitle = function () {
            return title;
        }
        this.setTitle = function (newTitle) {
            title = newTitle;
        }
        this.getViews = function () {
            return views;
        }
        this.addView = function (newView) {
            views.push(newView);
        }
        this.getView = function (i) {
            return views[i].getTitle();
        }
    };
});

And create new object when you consume the factory. 消耗工厂时创建新对象。

var workbook = new Workbook();

Please take a look. 请看一下。 Plnkr 普伦克

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM