1

If I push objects created on the fly, including another internal array of objects, to an array, how can I add objects only to a specific object's array. Using Reviews for example:

reviews.push({ 'reviewer' : 'John', 
               'review' : 'This movie was the greatest', 
               'comments' : { 'commenter' : 'Dave',
                              'comment' : 'The review by John was too short'} 
             });

'comments' being the internal array of objects.

If at a later stage I want to add objects only to a specific object's 'comments' by it's parents name/ID, is it possible? And if so how would I go about doing it?

Using the example, If there is only 1 review with multiple comments, and the comments come at a later stage, how can I add new comments to the 'comments' array within the review object?

I am guessing I would need to have a review ID to stop duplicates etc, but that aside I'm not even sure syntactically how to do it or if it's even possible.

Thanks in advance.

Aaron
  • 3,195
  • 5
  • 31
  • 49

3 Answers3

4

First off, comments should be an array and you have an object.

Then proceed like this:

reviews[someIndex].comments.push( { commenter: 'john', comment: 'hello!!'});

I.e.

if you need to add a comment to the first post do:

reviews[0].comments.push( { /* your comment */ } );

EDIT : I always used get() to retrieve an index but I seem to not be able to find much documentation about it, so I'm assuming (though I'm not sure) that [i] is a more standard way of doing things, hence why I changed the example. However the concept of pushing into comments doesn't change.

EDIT 2: OP wants to target a particular element in an array. I would use Array.prototype.indexOf as described here where you can find a solution for browsers that do not support indexOf as well.

Community
  • 1
  • 1
Joe Minichino
  • 2,793
  • 20
  • 20
  • 3
    Why `.get(i)` instead of `[i]`? – Barmar Aug 16 '13 at 09:22
  • I have to do it by the index? can I not target an object by reference? something (pseudo) like reviews.get('John').comments.push? Also 'First off, comments should be an array and you have an object' how so? – Aaron Aug 16 '13 at 09:26
  • I'm guessing your `get` is like: `Array.prototype.get = function (index) { return this[index]; };`? with maybe some error checking (like out-of-bounds indexing) – Halcyon Aug 16 '13 at 09:32
  • Can't have it both ways :) Either you retain native array methods so you can use push or you set object keys for uniqueness but then there's a risk you overwrite comments by mistake without proper checks in place. – Joe Minichino Aug 16 '13 at 09:33
  • This is great, but I can't target the element by a name or id, only an index? – Aaron Aug 16 '13 at 09:35
0

If you want to keep track of the reviews and comments by id's I'd do something like:

var reviews = {};
review_id = "#1234";
reviews[review_id] = {
    "reviewer": "John",
    "review": "This movie was the bestest",
    "comments": {
        "#456": {
            "commenter": "HAL 9000",
            "comment": "I'm afraid I can't let you do that Dave"
        }
    }
};

Adding a comment:

reviews[review_id].comments[comment_id] = { /* .. */ };
Halcyon
  • 57,230
  • 10
  • 89
  • 128
  • This looks interesting – Aaron Aug 16 '13 at 09:27
  • yeah it does but you give up native array utility methods like splice, push etc. – Joe Minichino Aug 16 '13 at 09:28
  • I doubt you'll need those methods, and you can make a similar implementation for objects. You probably just need a map or each function. It doesn't really matter. From a datamodeling point of view a dictionary (object) usually makes more sense than a list (array). – Halcyon Aug 16 '13 at 09:30
  • Won't that overwrite the previous comments in 'comments' array? – Aaron Aug 16 '13 at 09:36
  • I'm not sure what you mean. If you do: `a = {}; a["b"] = true; a["c"] = true;` you'll have two keys, `b` and `c`. You can overwrite them: `a["b"] = false;` and delete them: `delete a["b"];` – Halcyon Aug 16 '13 at 09:42
0
for(var i=0;i<reviews.length;i++){
if(reviews[i]["reviewer"]=="John"){
   var count=Object.keys(reviews[i].comments).length/2;
   reviews[i].comments["commenter"+(count+1)]="another commenter";
   reviews[i].comments["comment"+(count+1)]="some other comment";
   console.log(count);
}
}

output

commenter "Dave"

comment "The review by John was too short"

commenter2 "another commenter"

comment2 "some other comment"

http://jsfiddle.net/gkxcj/