Count the number of object in an array in JS - javascript

"abc":[{"a":"a"},{"b":"b"},{"c":"c"}];
I got this from my ajax's data callback, how can I know there's 3 object in it? I tried .length method but it grave me the wrong number.

Using .length on the array will give you the correct answer 3, but most likely you're doing data.length which is wrong in your case.
data["abc"].length will yield correct result.

Use Below code you will get 3 in console :
<script>
var test = {"abc":[{"a":"a"},{"b":"b"},{"c":"c"}]};
console.log("Length :"+test.abc.length);
</script>

It doesnt matter if you have objects in your array or other elements, array.length always works on it.
Readup: Array.length - JavaScript | MDN
The code that you have posted, it looks like abc is a property of an object.
var obj = {
"abc":[{"a":"a"},{"b":"b"},{"c":"c"}] // semicolon removed
};
alert(obj.abc.length); // compute length/number of objects here

Array.length will give you the number of elements in the array.
Your example
([{"a":"a"},{"b":"b"},{"c":"c"}].length == 3) // => true
So your issue lies elsewhere.

Related

Defining Array in Javascript doesn't work as expected

The following code:
let s=[[],[]];
let k=0;
while (k<(JSON.parse(req.responseText).length)){
s[k][0] =dataBack[k].ModuleCode;
s[k][1] =dataBack[k].ModuleDescription;
k=k+1;
}
Should populate an array (s) with the data from an Ajax responce.
But this is not the case, since when k=2 (3d item) I get an error:
code.js:288 Uncaught TypeError: Cannot set property '0' of undefined
Searching on StackOverflow, I found this link:
How to create empty 2d array in javascript?
describing what I have done to declare my Array.
I am expecting the above code to store the returned values into the (s) array.
But I get the error described above.
Change your code a bit to add arrays as needed:
let s=[];
let k=0;
while (k<(JSON.parse(req.responseText).length)){
s.push([]);
s[k][0] =dataBack[k].ModuleCode;
s[k][1] =dataBack[k].ModuleDescription;
k=k+1;
}
Hope this makes it clear why you're failing:
let s = [ [], [] ];
// ^^^^ s[0] ^^^^s[1]
Javascript will let you ASSIGN to positions in the array that don't exist yet.
eg:
var a=[];
a[10]=12345;
console.log(a);
//Output: [ <10 empty items>, 12345 ]
However in your code you are ACCESSING the undefined position first and then trying to modify what is returned.
Adding an intermediate step it might clear up why it doesn't work:
let s=[[],[]];
let k=0;
while (k<(JSON.parse(req.responseText).length)){
var tmp=s[k]; //When k>=2 tmp is undefined.
tmp[0] =dataBack[k].ModuleCode; //Trying to add a property at 0 on undefined object
tmp[1] =dataBack[k].ModuleDescription;
k=k+1;
}
#Oleg has given a nice work around in his answer but using s.push([]) to ensure the value you are accessing is definite for before the subsequent modifications.
Alternatively you could assign an empty array directly s[k]=[] before modification.

Comparing an array object to string using mocha && chai.

I am using mocha and chai for the first time and have no idea what is going on? im trying to say that my shuffle method has moved the array objects around and the first array object no longer - "sam1" IE -
describe('Shuffle', function(){
it('Shuffle should randomly move array items by their index', function(){
let group = ["sam1","sam2","sam3","sam4","sam5","sam6","sam7","sam8","sam9"];
let result = shuffle(group);
assert.equal(result, group[0] != "sam1");
});
});
this is the error -
AssertionError: expected [ Array(9) ] to equal true
how do i compare the two to make it true? or is there a better way to show the array has been shuffled?
The first argument of assert.equal() is where your comparison should be,
so
assert.equal(result, group[0] != "sam1");
should be
assert.equal(comparison, 'message to display on failure');
and a better way to know if the array has been shuffled would be to compare every element in the result with the original array, so something like
for(int i = 0; i < group.length; i++) {
if (group[i] !== result[i]) {
return false;
}
}
although, depending on how you shuffle there is a chance it shuffles in to the same order.
see http://www.chaijs.com/api/assert/ for more details on assert
It looks like shuffle returns an array. So to check if your first element in result array is not the same as in group array you have to compare the first two elements of arrays. If you want to use assert method, you have to do it this way:
assert(result[0] != group[0], "string if the test fails");
Just at the top of this doc
The easy way is to compare the previous array and after array. Don't use equal here but instead deepEqual to compare array or object.
it('Shuffle should randomly move array items by their index', function(){
let group = ["sam1","sam2","sam3","sam4","sam5","sam6","sam7","sam8","sam9"];
let result = shuffle(group);
assert.deepEqual(result, group);
});
});
Ref: http://www.chaijs.com/api/assert/#method_deepequal
Something like this?
assert.notEqual(group[0], "sam1");
You can find the list of usable functions here
http://www.chaijs.com/api/assert/
expect(result).to.have.members(group); // to check if all members there - doesn't care about the order
expect(result).to.not.eql(group); // to check if order has changed - there's a catch though; only 1 change on order (e.g. `shuffle` swapped **just** 2 members) is sufficient to this assertion to pass
Sources;
https://medium.com/building-ibotta/testing-arrays-and-objects-with-chai-js-4b372310fe6d
https://www.chaijs.com/api/bdd/#method_members
https://www.chaijs.com/api/bdd/#method_eql

Javascript Array Length Behavior

Let arr = [1,2,3,4]. If I set arr[x] where x >= arr.length, arr.length becomes x + 1.
This happens on Firefox and Chrome. I have two questions:
Is this defined behavior? (source would be welcome)
Is doing this recommended?
Thanks!
Is this defined behavior?
Yes, see ยง15.4 of the spec.
Is doing this recommended?
It depends entirely on what end result you want. There's nothing wrong with doing it.
You'll quite commonly see arrays built up like this:
var a = [];
for (/*...some loop over things...*/) {
a[a.length] = /* ...something to put on the array... */;
}
...which is exactly the same as:
var a = [];
for (/*...some loop over things...*/) {
a.push(/* ...something to put on the array... */);
}
Some JavaScript engines process the a[a.length] = ... faster than the a.push(...) (others are the opposite).
Note that JavaScript arrays are sparse, they can have gaps in them, which is part of the reason for this behavior. (In fact, JavaScript arrays aren't really arrays at all.) You can assign assign to the length property.
Array indexes start from zero.
arr[0] == 1
arr[1] == 2
arr[2] == 3
arr[3] == 4
When you set arr[4], it becomes the 5th element.
Sure, you could do this in JavaScript.
The array will extend to the xth index, and place your value there.
The length of the array will be x+1.
The values in the indexes in between that were never defined, 4 to x-1 in your case, will be undefined.

JavaScript array's length method

Can anyone explain why the second alert says 0 ?
var pollData = new Array();
pollData['pollType'] = 2;
alert(pollData['pollType']); // This prints 2
alert(pollData.length); // This prints 0 ??
The length of the array is only changed when you add numeric indexes. For example,
pollData["randomString"] = 23;
has no effect on length, but
var pollData = [];
pollData["45"] = "Hello";
pollData.length; // 46
changes the length to 46. Note that it doesn't matter if the key was a number or a string, as long as it is a numeric integer.
Besides, you are not supposed to use arrays in this manner. Consider it more of a side effect, since arrays are objects too, and in JavaScript any object can hold arbitrary keys as strings.
Because you haven't put anything into the array yet. You've only been assigning to a dynamically-created pollType attribute on the array object.
If you use numeric indices, then the array automagically takes care of length. For example:
var arr = [ ]; // same as new Array()
arr[2] = 'Banana!';
alert(arr.length); // prints 3 (indexes 0 through 2 were created)
The length property takes into consideration only those members of the array which names are indexes (like '1', '2', '3', ... ).
Arrays in JavaScript have numeric indexes only.
Use an object, which is essentially what you are doing above, setting properties on that array object.
array.length returns how many values are stored in the array. The first alert is returning the value of the position 'pollType'.
The reference guide I always use when needing help with javascript arrays is this page http://www.hunlock.com/blogs/Mastering_Javascript_Arrays
I'd also read what it says under the heading Javascript Does Not Support Associative Arrays, as you may run into problems with this also.
var pollData = Array();
function test() {
pollData[0] = 2
alert(pollData[0]);
alert(pollData.length);
}
//[x] is the array position; hence ['polltype'] is causing issues

Javascript (beginner): Performance issue using arbitrary numerical properties?

When I do something like this:
var o = new Array();
o[20] = true;
o[1000] = true;
o[4000] = true;
Is it reasonable to expect that only 3 elements will be allocated or can the implementation decide to suddenly allocate something with 4000 elements?
The reason I'm asking is that when I do this I see in firebug an indication that there are actually 4000 undefined in o. are they really there?
Now that we know that o is an Array, I can answer you precisely.
No, the elements will not be 'allocated' or 'created'.
When you make an assignment of an index property to an Array object, which is greater than the actual length of the array two things happen:
The index named property is created
The length property is incremented, to be the index + 1
For example:
var o = [];
o[4000] = true;
o.hasOwnProperty(0); // false, the property doesn't exist
o.hasOwnProperty(1); // false
o.hasOwnProperty(4000); // true, the property exist
As you can see, the hasOwnProperty method returns false when we test the presence of the 0 or 1 properties, because they don't exist physically on the object, whereas it returns true for 4000, the property that was created.
When Firebug detects that the object being printed in the console is an array-like object, it will simply make a loop, showing each of the index values from 0 to length - 1.
Firebug detects array-like objects simply by looking if they have a length property whose its value is an unsigned 32-bit integer (less than 2^32 - 1), and if they have a splice property that is a function, for example, the following object will be detected and printed as an Array on the Firebug's console:
console.log({length:3, splice:function(){}});
// Firebug will log: `[undefined, undefined, undefined]`
a) That code is not valid. You need either var o = {}; // object or var o = []; // array.
b) In the first case, the object is sparse. In the second, it may depend on the interpreter; in modern browsers it is also sparse. Try o[99999999] = "hi"; and see how much memory your browser does or does not allocate. If it does not go up by at least 10MB, your arrays are sparse.
I think this one answers the question.
Are Javascript arrays sparse?
And according to that one, arrays are spares, thats is, if you use for(item in array) you only get 3 items, not 4000 but if you use array.length it will take the larges integer value and return one larger, look here:
http://www.crockford.com/javascript/survey.html
Linkpad will use a for(item = 0; item < array.length; item++) and that one will return undefined for any index that is not present in the array.
/*
On the other hand, if you have a very large index any array manipulation will have to loop
through each index- it won't skip from one defined item to the the next defined item.
*/
var A= [];
A[0]= 'a';
A[10]= 'b';
A[4000000]= 'c';
alert(A.filter(function(itm){
return itm!= undefined;
}));
Javascript will generate all elements inbetween, always. You may want to use o.length to verify the length of the array. It will return 4000 and not 3.

Categories

Resources