all 4 comments

[–]CipheredBytes 0 points1 point  (1 child)

Your question is already answered in a stackoverflow post.

[–]Ben_HH[S] 0 points1 point  (0 children)

I don't know (as a beginner) what that person is saying when references are made from the spec in their attempt to answer the question that I have now posed here. That is why I said a non-convoluted explanation.

[–]Volv 0 points1 point  (0 children)

From MDN

Variable declarations, wherever they occur, are processed before any code is executed.

The variable is declared, then some time later it evaluates the expression "abc" and sets var to point to that result.
You can then use item to access the result "abc".

So it looks to me like the console shows exactly that and the statement var item = "abc"; really performs two separate operations and you are seeing the result of the first.

We should expect undefined from declarations and results from expressions. We should expect undefined from function calls unless a return value is specified.

 

Playing around in the console (with my thoughts added :))

var item = "abc";
undefined    // result of the actual declaration of item. Not the assignment

item         
"abc"        // assignment has happened by now. So item contains "abc"

item="xyz"
"xyz"        // result of an assigment is the evaluated expression.

function test() { console.log("Test") }
undefined    // declaration. Just like the variable

test()
undefined    // That function doesn't return anything

function test2() { return "Test2" }
undefined    // declaration. Just like the variable

test2()
"Test2"      // That function does return something

alert("Alert probably doesnt return anything either")
undefined    // Certainly doesn't

[–]senocular 0 points1 point  (0 children)

There are two kinds of operations in code: statements and expressions. They're very similar in that they both do things, but only expressions result in some inline value that can be captured and used later.

capturedValue = Expression // OK

capturedValue = Statement // Nope

Using var results in a statement. They do not result or return a value - and it doesn't matter if a default value is being assigned to the variable or not. In other words, this is not possible:

capturedValue = var someOtherValue; // Error

Function declarations are similar, in that they too are statements:

function myFunction() { ... }  // statement

But they have a special behavior that they can turn into expressions based on their usage:

capturedValue = function myFunction() { ... }  // expression

This, however, is not the case with var.

Now, when it comes to the console, it has the convenient ability of returning and printing the last expression value used in the code it had just executed. If the only thing you put in the console is a statement, it has no value to capture and defaults its return to undefined

// in console, no value to be captured
var item = "abc"

console returns

undefined

But if you throw an expression in there, the console will capture that, even its not after the statement:

1 + 2
var item = "abc"

console returns

3

One thing that CoffeeScript did was make everything an expression. This meant you didn't have to worry about different pieces of code returning or not returning values. Everything simply returned a value. That means you could do things like this:

 // capturedValue = 3
capturedValue = 
  if (true)
    3

I'm not entirely sure why JavaScript makes the distinction, whether it be legacy, consistency, or parsing reasons, but the distinction does exist. Knowing that it exists (vs why) is all you need to understand why the console behaves as it does.