43

I want to declare multiple variables in a function:

function foo() {
    var src_arr     = new Array();
    var caption_arr = new Array();
    var fav_arr     = new Array();
    var hidden_arr  = new Array();
}

Is this the correct way to do this?

var src_arr = caption_arr = fav_arr = hidden_arr = new Array();
Peter Mortensen
  • 28,342
  • 21
  • 95
  • 123
FFish
  • 10,538
  • 30
  • 89
  • 133

5 Answers5

83

Yes, it is if you want them all to point to the same object in memory, but most likely you want them to be individual arrays so that if one mutates, the others are not affected.

If you do not want them all to point to the same object, do

var one = [], two = [];

The [] is a shorthand literal for creating an array.

Here's a console log which indicates the difference:

>> one = two = [];
[]
>> one.push(1)
1
>> one
[1]
>> two
[1]
>> one = [], two = [];
[]
>> one.push(1)
1
>> one
[1]
>> two
[]

In the first portion, I defined one and two to point to the same object/array in memory. If I use the .push method it pushes 1 to the array, and so both one and two have 1 inside. In the second since I defined unique arrays per variable so when I pushed to one, two was unaffected.

meder omuraliev
  • 171,706
  • 64
  • 370
  • 423
19

Please stay away from that assignment pattern, even if you wanted to have all variables pointing to the same object.

In fact, only the first one will be a variable declaration, the rest are just assignments to possibly undeclared identifiers!

Assigning a value to an undeclared identifier (aka undeclared assignment) is strongly discouraged because, if the identifier is not found on the scope chain, a GLOBAL variable will be created. For example:

function test() {
    // We intend these to be local variables of 'test'.
    var foo = bar = baz = xxx = 5;
    typeof foo; // "number", while inside 'test'.
}
test();

// Testing in the global scope. test's variables no longer exist.
typeof foo; // "undefined", As desired, but,
typeof bar; // "number", BAD!, leaked to the global scope.
typeof baz; // "number"
typeof xxx; // "number"

Moreover, the ECMAScript 5th Strict Mode, disallows this kind of assignments. Under strict mode an assignment made to a non-declared identifier will cause a TypeError exception, to prevent implied globals.

By contrast, here is what we see if written correctly:

function test() {
    // We correctly declare these to be local variables inside 'test'.
    var foo, bar, baz, xxx;
    foo = bar = baz = xxx = 5;
}
test();

// Testing in the global scope. test's variables no longer exist.
typeof foo; // "undefined"
typeof bar; // "undefined"
typeof baz; // "undefined"
typeof xxx; // "undefined"
ToolmakerSteve
  • 5,893
  • 8
  • 67
  • 145
Christian C. Salvadó
  • 723,813
  • 173
  • 899
  • 828
  • mmm, so the best way is: var one_arr = []; var two_arr = []; I was wondering about the difference between declaration and assignment. So only the first one is declared? – FFish Nov 02 '10 at 22:39
  • 1
    @FFish: In the above example, the `var` statement is used only in the `foo` identifier, the rest of assignments at the right are evaluated from *right-to-left*, due the associativity of the assignment operator, (Imagine: `var foo = value;` where `value` is the expression with multiple assignments (`bar = baz = xxx = 5`), they have nothing to to with the `var` statement.) However you can use commas to declare multiple variables with a single `var` statement: `var one_arr = [], two_arr = [], three_arr = [];` – Christian C. Salvadó Nov 02 '10 at 22:53
1

No, your second statement will create four references to the same array. You want:

var src_arr     = [],
    caption_arr = [],
    fav_arr     = [],
    hidden_arr  = [];
Peter Mortensen
  • 28,342
  • 21
  • 95
  • 123
hvgotcodes
  • 109,621
  • 25
  • 195
  • 231
0

All those variables will refer to one Array object.

Peter Mortensen
  • 28,342
  • 21
  • 95
  • 123
heximal
  • 9,973
  • 5
  • 40
  • 66
0

For all intents and purposes the literal [] notation syntax should be used. Since the Array constructor is ambiguous in how it deals with its parameters.

From the docs:

If the only argument passed to the Array constructor is an integer between 0 and 232-1 (inclusive), this returns a new JavaScript array with its length property set to that number. And that implies Array of passed length of empty slots with undefined values.

new Array(1, 2, 3); // Result: [1, 2, 3]
new Array(3); // Result: [empty × 3] with undefined at indexes
new Array('3') // Result: ['3']

//this was ambiguous
let x = new Array(5); // Result: [empty × 5]
x.push("Hello"); //expected x as ["Hello", empty, empty, empty, empty]
//Actual x: [empty × 5, "Hello"]

Destructuring syntax:

Another neater way to declare multiple variables is using destructuring assignment which enables unpacking values from arrays, or properties from objects, into distinct variables.

function foo() {
  //destructuring assignment syntax
  let [src_arr, caption_arr, fav_arr, hidden_arr] = [[], [], [], []];

  console.info("Variables::", fav_arr, hidden_arr, caption_arr, src_arr);

  fav_arr.push("fav");
  hidden_arr.push("hidden");

  //After adding some values to couple of arrays
  console.info("Variables::", fav_arr, hidden_arr, caption_arr, src_arr);
}

foo();
ambianBeing
  • 2,648
  • 2
  • 9
  • 19