0

In JavaScript, Why objects cannot be accessed before instantiation unlike function declaration which moves the declaration to the top of its scope and can be called irrespective of its position in the literal code.

Example:

    for(var property in myObj)
            alert(myObj[property].toString());
        var myObj = {
            property1: "chocolate",
            property2: "cake",
            property3: "brownies"
        }

Above does nothing not even an error/ log entry in Console. Why?

5 Answers 5

4

Because that's just how the language is designed. Only function declarations and variable declarations (but not initialization) are hoisted. So your code is really:

var myObj = undefined;
var property = undefined;

for(property in myObj)
    alert(myObj[property].toString());
    myObj = {
        property1: "chocolate",
        property2: "cake",
        property3: "brownies"
    };
}

...which fails not because the variable myObj doesn't exist yet (it does), but because that variable has the value undefined, and you can't use for-in on undefined.

If you think about it, it makes reasonable sense: A function declaration creates a unit of work (a function) based only on its own content, and then is executed later (with any variables it closes over evaluated later, when it's executed), but an object initialization can rely on other things (like variables and such) which would need to be evaluated as of the initialization, not later.

Example:

var answer = 42;
var obj = {
    property: answer
};

The declaration of obj and answer are hoisted, but it's impossible to hoist the creation of the object we assign to obj, because it has to use the value of the answer variable in order to initialize the property property.

In contrast:

var answer = 42;
foo();
function foo() {
    console.log("The answer is " + answer);
}

Both the declaration of answer and the declaration/creation of the foo function are hoisted, and that's fine, because although foo uses answer, it doesn't use it until later, when it's called.

Sign up to request clarification or add additional context in comments.

Comments

0

That is because functions declare only definition, and this definition could be visible in all your code. Of course in proper scope.

function test() {
}

However by defining variables, you create physical object. It is created just in time of executing this line of code, so it is not visible earlier.

var testData = {};
var testFunction = function() {
}

Comments

0

Firstly, hoisting makes this code work as if it was:

var myObj = undefined;
for(var property in myObj)
        alert(myObj[property].toString());
    myObj = {
        property1: "chocolate",
        property2: "cake",
        property3: "brownies"
    }

Therefore, myObj is undefined when for-in loop executes. The fact that myObj has no properties (its undefined at that point) makes for-in loop not execute any single time (that is why you don't receive any error).

Comments

0

Function declarations and variable declarations are always moved (“hoisted”) invisibly to the top of their containing scope by the JavaScript interpreter.

Functions are hoisted with the body. So you have complete function that you can call anywhere.

Variable assignments will not be hoisted. Only names declaration. This is not the case with function declarations, where the entire function body will be hoisted as well.

So:

console.log(i); // i is undefined
var i = 1;      // value is assigned 
console.log(i)  // now we get the value

i is visible anywhere (with undefined as value) because its been hoisted by the interpreter to the top of scope. But not assigned yet. It assigns when the execution comes to that line of code.

Read more at enter link description here

Comments

-1

It depends on how you define a function.

For example, this function wouldn't be available too:

func();
// This is a function expression instead of a declaration
var func = function() {};

At the end of the day, you can't use an object literal before instantiating it (see I'm not saying declaring) since it's stored in a reference (i.e. a variable) that won't exist until it's declared!

When declaring functions...

doStuff();
function doStuff() { }

...works because doStuff is declared once JavaScript run-time has already parsed the code, while the approach of setting a function to some variable happens when the code is actually hit.

TL;DR version...

An object literal is assigned to some variable and you won't be able to access a variable before it's declared. This is the simplest way of explaining your concern.

3 Comments

@T.J.Crowder Is it fine now?
Yes, although to my mind it doesn't really answer the question. (My opinion on that doesn't really matter, though. :-) )
@T.J.Crowder It doesn't go into the quircks of how it works this way... I still think it answers the question. It's not the same trying to access a variable before it's declared than declaring a function.

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.