2

I am trying to learn about closures in javascript and I came across the following example:

function counter() {
    var count = 0;
    return function() {
        alert(count++);
    }
}
var count = counter();
count();
count();
count();

Which makes sense to me, my question is, why doesn't this work?

var count = function() {
    var count = 0;
    return function() {
        alert(count++);
    }
};
count();
count();
count();

To me it seems like it should be the exact same thing but maybe I'm just missing something obvious, please assist.

0

3 Answers 3

2

In order for your second method to work, you will need to call the returned function like this:

var count = function() {
    var count = 0;
    return function() {
        alert(count++);
    }
};
count()();

However, doing this, your count number will not increase because it is not being stored anywhere like in the first example, where the variable count holds the function.

So if you want to retain the value of count, use the first method where you say var count = counter()

Hope that clears things up!

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

Comments

1

I'll try to give a nice explanation right in your code:

function counter() {
    var count = 0;

    // By calling the function counter (adding a '()' after its name) you are returning a brand new anonymous function
    return function() { // **Reference 1**
        alert(count++);
    }
}

// Here, the count variable is actually the anonymous function you returned in the **Reference 1**
var count = counter();

// In this line, you are calling the anonymous function (adding the '()' after its new name 'count')
count();

The explanation above explain why this works. Because, first you called a function which returned an anonymous function and assigned it to the variable count. Then you called that function by adding the '()' after its name, which executes the alert(count++)

Now, why the other example does not work? I guess it's pretty obvious now:

var count = function() {
    var count = 0;
    return function() { // **Reference 2**
        alert(count++);
    }
};

// Here you are calling the count function which returns the anonymous function in the line **Reference 2**.
count(); // So, long story short, this call only returns the anonymous function.

You should try to add a second '()' after it: count()();. This should work as well, because the first '()' returns the anonymous function, and the second one, executes the anonymous function returned.

Hope this helps!

2 Comments

thank you everyone, all your answers were helpful, I just appreciate going the extra mile here and explaining the answer within the code, I completely understand now.
Great @SeptimaEspada. This is a very simple concept and very useful for Javascript advanced programming. More than glad to help you! :)
0

Before you can use the closure, you have to call the outer function to create the closure and get the inner function that is returned and then retain that return result that you can then call subsequent times to use the closure. So, in your second example, you have to call count() and retain it's return result and then use that return result for subsequent calls.

Your second example will work if you change it to this (which looks pretty much the same as the first example):

// log output for purposes of the snippet
function log(x) {
    var div = document.createElement("div");
    div.innerHTML = x;
    document.body.appendChild(div);
}

var counter = function() {
    var count = 0;
    return function() {
        log(count++);
    }
};
// get the inner function and create the closure
var count = counter();
count();
count();
count();

As you can see this only differs from your first example in that counter is a function expression instead of a function definition. Other than the timing of when counter is defined, the second code example is no different and thus the implementation needs to be the same.

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.