Challenge - Basic JavaScript: Record Collection

Tell us what’s happening:
I just tried to did this lesson and I was struggling to work out so I clicked the “get hint” and it took me the official answer. The code/solution works from the hint page but I am struggling understand how (I worked it out a different way). Prob better if you read the original post first (it’s not long) but a snippet is of below. His code is:

The answer is...

and the explanation is:

Code Explanation

  • First checks if prop is equal to tracks AND if value isn’t a blank string. If both tests pass, value is pushed into the tracks array.
  • If that first check doesn’t pass, it next checks only if value isn’t a blank string. If that test passes, either a new key ( prop ) and value ( value ) are added to the object, or an existing key is updated if the prop already exists.
  • If both these checks fail (meaning value must be an empty string), then the key ( prop ) is removed from the object.
    Challenge: Record Collection

The explanation says “the first check is …” but what he says is the first check looks to me is the second check - the first line of code deletes a property. The the other explanations don’t match the code either, am I right in this or have I missed something?

Although the explanations don’t seem to match the code I can see how it works except for one line:

collection[id][prop] = collection[id][prop] || ;

This line clearly refers to the part in the challenge where it says you are meant to create a blank array if the “prop” isn’t populated (see challenge for more detail). My line of code was:

if (!collection[id][prop] ){collection[id][prop]=};

which translate to “if the property doesn’t exist then create a new blank array” (what the challenge tells you to do). But somehow, his code meets this criteria as well, because it passes the tests. Can someone please explain this line or is it just that the challenge acceptance script isn’t working properly? In particular I thought that || meant OR but in this case does it mean something different?

Link to the challenge:

3 Likes

I don’t know why the hints and solution do not match

but for your question

|| is the OR logical operator, you are right
when you have two values like a || b, if a is a truthy value the expression resolve as a, if a is a falsy value the expression resolve as b
in this case if collection[id][prop] is truthy (and an array with values inside is truthy) it is left as it is, if it is falsy (undefined is falsy) then an empty array is assigned to it

6 Likes

I agree the solution verbiage is not correct. But I am also curious here.

These two are the same for me:

Maybe I’m missing something as well?

Either works in the challenge for me (Chrome) when uncommented:

// Only change code below this line
function updateRecords(id, prop, value) {
if(value === '') delete collection[id][prop];
else if(prop === 'tracks') {
//collection[id][prop] = collection[id][prop] || [];
//if (!collection[id][prop]) { collection[id][prop] = [] };
collection[id][prop].push(value);
} else {
collection[id][prop] = value;
}
return collection;
}
// Alter values below to test your code

they do the same function, one is shorter than the other tho

1 Like

yup. I agree, I was confused at first, but tested it myself and see no difference.

@graham Let us all know if you can produce the same result, or post your full solution here. Both the if(!) and || approaches you mentioned above work for me (Chrome)

I get it that it works, I already said that, my questions is why? I don’t seem to understand the code for that line. Can you some break each part down please. Here is my understanding of it.

collection[id][prop] = collection[id][prop] || ;

assign collection[id][prop] to collection[id][prop] OR create new array

That isn’t the same as an “if statement” to check a value of true of false. It doesn’t check to see if the “prop” value exists first. Is my interpretation correct? If yes, then isn’t the solution wrong even though it passes the JS checks?

Graham

1 Like

when you have

if (!collection[id][prop]) {
   collection[id][prop] = []
}

this is checking if collection[id][prop] has a falsy value (as a falsy value with ! makes true, the if statement execute if it has a falsy value), and if it has then it is setting it to []

what probably I missed saying here is that whatever the expression with || resolves to, that is what it is assigned to the variable

collection[id][prop] = collection[id][prop] || []
// if collection[id][prop] has truthy value it becomes
collection[id][prop] = collection[id][prop] // nothing changes
// if collection[id][prop] has falsy value it becomes
collection[id][prop] = []

undefined is falsy

2 Likes

Well that’s a bit of a curve ball because all lessons and challenges so far say that one equals sign means to assign a value and two equals sign is used for a comparison. In this example it isn’t the case, it seems it is a shorthand for a simple if statement, I guess I just haven’t gotten that far in the curriculum yet where it shows this type of syntax.

Thanks for the explanation.

1 Like

it is not exactly a shorthand for an if statement, it is just that in this situation the two things have the same function

look at the definition of the operators in the table:

2 Likes

that link helps thanks

function updateRecords(id, prop, value) {
  if (value === ""){
    delete collection[id][prop];
  }else if (prop === "tracks"){
    if (collection[id].hasOwnProperty("tracks") == true){
      collection[id][tracks].push(value);
    }else{
      collection[id][tracks] = [];
      collection[id][tracks].push(value);
    }
  }else{
    collection[id][prop] = value;
  }


  return collection;
}

help me guys, where is the problem?

Do you have a variable named tracks?

1 Like

collection[id][tracks].push(value);

There is no variable named tracks. Use the variable name instead.

1 Like

why we cannot use collection.id.prop instead of collection[id][prop] ?

Please explain

3 Likes

Because id and prop are variables. You have to use bracket notation if you want to look up properties using variables.

3 Likes

collection.id would be looking for a property on collection named id, not one named (for example) collection.2496 (assuming id==2496).

Using bracket notation, you can use strings or variables to access properties. Not only does that allow for variables, but also questionable property names.

3 Likes

Thanks @bbsmooth and @snowmonkey for explaining this!

@maxchernyshou

You can post solutions that invite discussion (like asking how the solution works, or asking about certain parts of the solution). But please don’t just post your solution for the sake of sharing it.

We have set your post to unlisted. Thanks for your understanding.

Holy Shetland pony I have been working on this for 4 days absolutely wracking my brain. I would really love some help here.
@graham Thanks for bringing this up.

function updateRecords(id, prop, value) {
  if (value === "") {
    delete collection[id][prop];
  } else if (prop === "tracks") {
//when this code is used as written it works.
collection[id][prop] = collection[id][prop] || [];
// if this is operating as an OR why doesn't it work when switched around? 
//  collection[id][prop] = [] || collection[id][prop] 
//@ieahleen  isn't everything to the right of the "="  resolved before being assigned to the property to the left?
 collection[id][prop].push(value);
  } else {
    collection[id][prop] = value;
  }
  return collection;

}

//as an alternative to the OR operator I've been trying to use this to detect an array to no avail:  if(collection[id][prop].hasOwnProperty([]))
//Thanks again!

People have explained better than me, so I will give you a link to check.
Look this article, see if you get it:


I’ve edited your post for readability. When you enter a code block into a forum post, please precede it with a separate line of three backticks and follow it with a separate line of three backticks to make it easier to read.

See this post to find the backtick on your keyboard. The “preformatted text” tool in the editor (</>) will also add backticks around text.

Note: Backticks are not single quotes.

markdown_Forums

1 Like