0

I have an array of objects with the following format:

obj = { ref: 8, id: "obj-8" }

and a function which uses jQuery's grep method to return an item from that array, by searching for the object ref property:

function returnObj(arr,r){
    return $.grep(arr, function(elem,index){ return elem.ref == r; })[0];
}

If I use this function on an array that has undefined elements in it (they were previously deleted using the delete operator), I get the following error: Uncaught TypeError: Cannot read property 'ref' of undefined, which I assume is thrown when an undefined element is encountered.

How can I modify the function so it doesn't break?

2
  • return elem && elem.ref == r; Commented Oct 3, 2012 at 17:07
  • 1
    also, why use $.grep when it essentially does the same thing as Array.filter? Commented Oct 3, 2012 at 17:09

3 Answers 3

2

Just check to see if the current item is undefined, or simply "falsey" if you expect specifc objects, and return false if so.

function returnObj(arr,r){
    return $.grep(arr, function(elem,index){ 
                           return elem ? elem.ref == r : false;
                       })[0];
}

Here's another option. Since you're using delete to remove the items, you can use the native .filter method, which skips over non-existent array members.

function returnObj(arr,r){
    return arr.filter(function(elem){ elem.ref == r})[0];
}
Sign up to request clarification or add additional context in comments.

5 Comments

How do I do that exactly? I'm not exactly sure I understand the code line "return elem.ref == r;" (the function was written by someone else) so I'm finding it difficult to modify it.
@AndreiOniga: That's a conditional operator. Basically it says "if elem evaluates to a true value, return the result of elem.ref == r otherwise return false"
@AndreiOniga: If you're saying you don't understand the way it was originally written, basically $.grep evaluates the returned value as true or false evaluations. If a "truthy" value is returned, it adds the current item to the new Array it is building. If "falsey" it doesn't. Then your function is simply returning the first item in the resulting Array.
@AndreiOniga: One more thing. You should be aware that delete leaves a hole in the Array. It doesn't re-index the Array, resulting in a shorter Array. If you want the Array to be reindexed when something is removed, then use .splice(). arr.splice(idx, 1) This will remove 1 item located at the given idx, and will resolve your issue with undefined items.
Well, it seems that I understood the delete op. and splice() method the other way around, that's the only reason why. Now that you've mentioned it, I swapped them. :) Thanks again!
1

just check that it's not undefined:

function returnObj(arr,r){
    return $.grep(arr, function(elem,index){
        return elem ? elem.ref == r : false; 
    })[0];
}

Comments

1

I believe you could simply add a test for undefined:

return $.grep(arr, function(elem,index){ return elem != undefined && elem.ref == r; })[0];

But I'm not sure why you're using $.grep. You could use the existing Array.filter to achieve the same result:

function returnObj(arr,r){
    return arr.filter(function(ele,index){return ele && ele.ref == r;})[0];
}

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.