Reputation: 28513
I want to loop over an array called children
which may or may not be defined.
Currently I'm doing this:
var i;
var foo = {/*"children": ["1","2","3","4"]*/};
for (i = 0; i < [foo.children || []][0]. length; i += 1) {
console.log("hello")
}
This works correctly, because in case children
is undefined, [foo.children || []][0]
ends up being [[]]
whose first element is an empty array []
.
Question:
Is there any way to leave away the outer array?
I don't want to use an if-clause testing for children, just modify the array.
One way would be:
for (i = 0; i < foo.children.length || [].length; i += 1) {
console.log("hello")
}
but I'm looking for other alternatives if exist.
Thanks
EDIT: Here is a jsperf on all variants. Interesting...
Upvotes: 0
Views: 149
Reputation:
Why not using a function to hide all these dirty statements?
function each(array, fn) {
if (array) {
var i = -1;
while (++i < array.length) {
if (fn(array[i]) === false) return;
}
}
}
Upvotes: 0
Reputation: 27833
EDIT: According to comments on other answers the OP wants terse, but jsLint appropriate code. Here it is:
var i, c, foo = {}, console;
for (i = 0, c = foo.children; i < (c && c.length); i += 1) {
console.log("hello");
}
I will leave the other possibilitis here for people who don't have as strict requirements as the OP does.
You can use the &&
operator:
for (i = 0; i < (foo && foo.children && foo.children.length); i += 1) {
console.log("hello")
}
If there is a chance that foo
is not defined at all, then you need something slightly worse:
for (i = 0; i < ((typeof foo === 'object') && foo.children && foo.children.length); i += 1) {
console.log("hello")
}
Or if you're sure that foo
is an object, you can skip the first check:
for (i = 0; i < (foo.children && foo.children.length); i += 1) {
console.log("hello")
}
Upvotes: 1
Reputation: 706
You could add a condition checking the existence of the array to your for loop like this:
for (i = 0; (typeof foo.children != 'undefined') && (i < foo.children.length); i++) {
// do something
}
/edit:
OK, others were a bit faster than me, and foo.children
is a nice alternative to typeof foo.children != 'undefined'
;)
Upvotes: 0
Reputation: 2810
Another possible way:
for (i = 0; foo.children && i < foo.children.length; i += 1)
Upvotes: 0
Reputation: 664969
Use parenthesis instead of that one-item-array:
for (i = 0; i < (foo.children || []).length; i += 1) {
or move it further outside:
for (i = 0; foo.children && i < foo.children.length; i += 1) {
which is very near to
if (foo.children) for (i = 0; i < foo.children.length; i += 1) {
which would indeed be the cleanest way. There's nothing wrong with an if-statement.
Upvotes: 2
Reputation: 781721
var len = foo.children ? foo.children.length : 0;
for (i = 0; i < len; i++) {
...
}
Upvotes: 3