0
var repeatelem = function(elem, n){
            // returns an array with element elem repeated n times.
            var arr = [];
            for (var i=0; i<n; i++) {
              (function(newValue, index){
                                console.log(index)
                                Object.defineProperty(newValue, 'reasonId', {
                                    value:index,
                                    configurable:true
                                });
                              arr = arr.concat(elem);
                        }(elem, i))

            };
            return arr;
        };
        var res = repeatelem({a:1},3)
        console.log(res)

OUTPUT : OUTPUT

I was excepting the reasonId to be 0,1,2. not sure, why there is a problem here even after using closures the value of reasonId set to last index value.

Plunkr

Excepted :

[{a:1,'reasonId':0 }, {a:1,'reasonId':1 }, {a:1,'reasonId':2 }]
RONE
  • 5,415
  • 9
  • 42
  • 71

1 Answers1

1

Javascript variables that contain objects, really contain a reference to the object, so you're closure properly copies the value of i, but elem and newValue are the same object. No copying is done.

So when you run arr.concat(elem) (which I think you meant arr.concat(newValue)) you are concatenating the same object into your array repeatedly.

You need to make a copy of your object, before you append it to the array. See How do I correctly clone a JavaScript object? . The closure is also unnecessary in your case; that is usually used to solve issues when there is asynchronous code in the loop. You can simplify your code to:

var repeatelem = function(elem, n){
    // returns an array with element elem repeated n times.
    var arr = [];
    for (var i=0; i<n; i++) {
        var copy = Object.assign( {}, elem );
        Object.defineProperty( copy, 'reasonId', {
            value: i,
            configurable: true
        });
        arr.push( copy );
    }
    return arr;
};

Where Object.assign is being used to make a shallow copy. It is an ES6 function that can be shimmed for this use-case . Be aware that this is only a shallow copy and if the elements can have objects in their own properties you probably want a deep copy instead, otherwise each element will share their child objects with each other, so when you modify one child, they all change.

Community
  • 1
  • 1
Paul
  • 139,544
  • 27
  • 275
  • 264