This question already has answers here:
Closed 10 years ago.
Possible Duplicate:
What do parentheses surrounding a JavaScript object/function/class declaration mean?
What does this “(function(){});”, a function inside brackets, mean in javascript?
A Javascript function
I encountered markup similar to this:
var something = (function(){
//do stuff
return stuff;
})()
document.ondblclick = function(e) { alert(something(e)) };
I don't understand the opening ( and closing )() in the something variable.
Could you explain the difference to writing it like this?
var something = function(){
//do stuff
return stuff;
};
Thanks!
It's probably easier to understand if you leave the redundant parens out because they serve no purpose:
var something = function() {
return 3;
} // <-- a function.
(); // now invoke it and the result is 3 (because the return value is 3) assigned to variable called something
console.log(something) //3 because the function returned 3
var something = function() {
return 3;
}; // a function is assigned to a variable called something
console.log(something) //logs the function body because it was assigned to a function
console.log(something()) //invoke the function assigned to something, resulting in 3 being logged to the console because that's what the function returns
(function(){ ... }) is a (anonymous) function expression, you could e.g. assign that value to a variable.
The brackets behind it will immidiately execute the function expression, resulting in the return value of the function (in here: stuff). The construct is called IIFE.
When stuff is a function (which I assume, because you invoke something lateron), this is called a closure - the returned function (stuff, assigned to something) still has access to the variables in the execution context of that anonymous function.
On the question what it does, read all the comments and other answers. They are absolutely right.
Why would you want to use it? You find this pattern very often when using closures. The intent of the following code snippet is to add an event handler to 10 different DOM elements and each one should alert it’s ID attribute (e.g. “You’ve clicked 3″). You should know that if this was your actual intent, then there is a much easier way to do this, but for academic reasons let’s stick with this implementation.
var unorderedList = $( "ul" );
for (var i = 0; i < 10; i++) {
$("<li />", {
id: i,
text: "Link " + i,
click: function() {
console.log("You've clicked " + i);
}
}).appendTo( unorderedList );
}
The output of the above code may not be what you first expect. The result of every click handler will be “You’ve clicked 9″ because the value of i at the point the event handler was fired is “9″. What the developer really wanted is for the value of i to be displayed at the point in time the event handler was defined.
In order to fix the above bug we can introduce a closure.
var unorderedList = $( "ul" ), i;
for (i = 0; i < 10; i++) {
$("<li />", {
id: i,
text: "Link " + i,
click: function(index) {
return function() {
console.log("You've clicked " + index);
}
}(i)
}).appendTo( unorderedList );
}
You can execute and modify the above code from jsFiddle.
One way to fix the above code is to utilize a self-executing anonymous function. That is a fancy term that means we are going to create a nameless function and then immediately call it. The value of this technique is that the scope of the variable stays within the function. So, first we will surround the event handler content in a function and then immediately call the function and pass in the value of i. By doing that, when the event handler is triggered it will contain the value of i that existed when the event handler was defined.
Further reading on closures: Use Cases for JavaScript Closures
All of the answers were good, but I think the simplest answer has been skimmed over:
var something = (function(){
//do stuff
return stuff;
})()
After this code executes, something becomes stuff. The function that returned stuff is executed before something is assigned.
var something = function(){
//do stuff
return stuff;
};
After this code executes, something is a function which returns stuff. The function that returns stuff was never executed.
Check the JavaScript FAQ section, too: Here are some pretty good explanations and examples
Ok, why should you use this:
Suppose my script is running, and there are a couple of things (I'm, for instance, looping through a nodes list) I might be needing later on. That's why I might choose to do something like this:
for(var i=0;i<nodesList.lenght;i++)
{
if (nodesList[i].id==="theOneINeed")
{
aClosure = (function(node,indexInNodesList)//assign here
{
return function()
{
node.style.display = 'none';//usable after the parent function returns
alert(indexInNodesList+ ' is now invisible');
}
})(nodesList[i],i);//pass the element and its index as arguments here
break;
}
}
i = 99999;
aClosure();//no arguments, but it'll still work, and say i was 15, even though I've just
//assigned another value to i, it'll alert '15 is now invisible'
What this enables me to do is to prevent function arguments from being garbage collected. Normally, after a function returns, all its var's and arguments are GC'd. But in this case, the function returned another function that has a link to those arguments (it needs them), so they're not GC'ed for as long as aClosure exists.
As I said in my comment. Google closures, practice a bit, and it'll dawn on you... they really are quite powerful
Related
This question already has answers here:
JavaScript closure inside loops – simple practical example
(44 answers)
Closed 6 years ago.
I have read a number of explanations about closures and closures inside loops. I have a hard time understanding the concept. I have this code: Is there a way to reduce the code as much as possible so the concept of closure can be made clearer. I am having a hard time understanding the part in which the i is inside two parenthesis. Thanks
function addLinks () {
for (var i=0, link; i<5; i++) {
link = document.createElement("a");
link.innerHTML = "Link " + i;
link.onclick = function (num) {
return function () {
alert(num);
};
}(i);
document.body.appendChild(link);
}
}
window.onload = addLinks;
WARNING: Long(ish) Answer
This is copied directly from an article I wrote in an internal company wiki:
Question: How to properly use closures in loops?
Quick answer: Use a function factory.
for (var i=0; i<10; i++) {
document.getElementById(i).onclick = (function(x){
return function(){
alert(x);
}
})(i);
}
or the more easily readable version:
function generateMyHandler (x) {
return function(){
alert(x);
}
}
for (var i=0; i<10; i++) {
document.getElementById(i).onclick = generateMyHandler(i);
}
This often confuse people who are new to javascript or functional programming. It is a result of misunderstanding what closures are.
A closure does not merely pass the value of a variable or even a reference to the variable. A closure captures the variable itself! The following bit of code illustrates this:
var message = 'Hello!';
document.getElementById('foo').onclick = function(){alert(message)};
message = 'Goodbye!';
Clicking the element 'foo' will generate an alert box with the message: "Goodbye!". Because of this, using a simple closure in a loop will end up with all closures sharing the same variable and that variable will contain the last value assigned to it in the loop. For example:
for (var i=0; i<10; i++) {
document.getElementById('something'+i).onclick = function(){alert(i)};
}
All elements when clicked will generate an alert box with the number 10. In fact, if we now do i="hello"; all elements will now generate a "hello" alert! The variable i is shared across ten functions PLUS the current function/scope/context. Think of it as a sort of private global variable that only the functions involved can see.
What we want is an instance of that variable or at least a simple reference to the variable instead of the variable itself. Fortunately javascript already has a mechanism for passing a reference (for objects) or value (for strings and numbers): function arguments!
When a function is called in javascript the arguments to that function is passed by reference if it is an object or by value if it is a string or number. This is enough to break variable sharing in closures.
So:
for (var i=0; i<10; i++) {
document.getElementById(i).onclick =
(function(x){ /* we use this function expression simply as a factory
to return the function we really want to use: */
/* we want to return a function reference
so we write a function expression*/
return function(){
alert(x); /* x here refers to the argument of the factory function
captured by the 'inner' closure */
}
/* The brace operators (..) evaluates an expression, in this case this
function expression which yields a function reference. */
})(i) /* The function reference generated is then immediately called()
where the variable i is passed */
}
I've been programming in JavaScript for a long time, and "closure in a loop" is a very broad topic. I assume you are talking about the practice of using (function(param) { return function(){ ... }; })(param); inside of a for loop in order to preserve the "current value" of the loop when that inner function later executes...
The code:
for(var i=0; i<4; i++) {
setTimeout(
// argument #1 to setTimeout is a function.
// this "outer function" is immediately executed, with `i` as its parameter
(function(x) {
// the "outer function" returns an "inner function" which now has x=i at the
// time the "outer function" was called
return function() {
console.log("i=="+i+", x=="+x);
};
})(i) // execute the "closure" immediately, x=i, returns a "callback" function
// finishing up arguments to setTimeout
, i*100);
}
Output:
i==4, x==0
i==4, x==1
i==4, x==2
i==4, x==3
As you can see by the output, all of the inner callback functions all point to the same i, however, since each had its own 'closure', the value of x is actually stored as whatever i was at the time of the outer function's execution.
Commonly when you see this pattern, you would use the same variable name as the parameter and the argument to the outer function: (function(i){ })(i) for instance. Any code inside that function (even if executed later, like a callback function) is going to refer to i at the time you called the "outer function".
Well, the "problem" with closures in such a case is, that any access to i would reference the same variable. That is because of ECMA-/Javascripts function scope or lexical scope.
So to avoid that every call to alert(i); would display a 5 (because after the loop finished i === 5), you need to create a new function which invokes itself at runtime.
To achieve this, you need to create a new function, plus you need the extra paranthesis at the end, to invoke the outer function immediately, so link.onclick has now the returned function as reference.
A closure is a construct in which you reference a variable outside the scope in which it's defined. You usually talk about closures in the context of a function.
var helloFunction;
var finished = false;
while (!finished) {
var message = 'Hello, World!';
helloFunction = function() {
alert(message);
}
finished = true;
}
helloFunction();
Here, I define the variable message, and define a function that references message. When I define the function to use message, I am creating a closure. This means helloFunction holds a reference to message, so that I can continue to use message, even outside of the scope (the loop body) where message is defined.
Addendum
The (i) in parenthesis is a function call. What's happening is:
You define some function(num) {}. This is called an anonymous function, because it's defined inline and doesn't have a name.
function(num) takes an integer argument, and returns a reference to another function, which is defined as alert(num)
The outer anonymous function is immediately called, with the argument i. So num=i. The result of this call is a function which will do alert(i).
The end result is more or less equivalent to: link.onclick = function() { alert(i); };
To answer the last part of your questions. The two parenthesis invoke the function as any other functions. Why you do it here is that you want to keep what the variable "i" is just at that time. So what it does is, invoke the function, the i is sent as a argument "num". Since it's invoke it will remember the value nume in variable links own scoop.
If you did't to this all link click would result in an alert saying "5"
John Resig, founder of jQuery, has a really nice online presentation explaining this. http://ejohn.org/apps/learn/
..fredrik
I'm learning to code Chrome Extensions and I'm curious about passing parameters into asynchronous functions and a possible concurrency issue. Let me give you an example:
function updateActiveTab(param1)
{
chrome.tabs.query({active: true, currentWindow: true}, function(tabs)
{
onUpdatingTab(tabs[0].id, param1);
});
}
function onUpdatingTab(tabID, param1)
{
console.log("Tag ID=" + tabID + ", param=" + param1);
}
So, lets assume that the first time my updateActiveTab() method is called with param1=1 and the call to chrome.tabs.query() takes a while. In the meantime, while chrome.tabs.query() is still being processed, my updateActiveTab() method is called again with param1=2. What would happen when the first call to chrome.tabs.query() returns and begins processing its callback function? Will param1 be 1 or 2?
I'm obviously looking to pass my param1 as 1, and 2, and so on, to its function's respective calls.
The short answer is that you will win. Read up on JavaScript closures to really understand what's going on here. I'll hit the highlights so you get the idea.
The reference to param1 inside of onUpdatingTab forces param1 into a closure. The closure keeps the value of param1 alive as long as it is needed by calls to inner functions. The scenario you describe will create two different closures, one for each call to onUpdatingTab.
Here's an example adapted from JavaScript: The Good Parts that illustrates this aspect of closures. This function takes an array of DOM nodes and adds an onclick handler that displays the ordinal of the node:
function add_the_handlers = function (nodes) {
var helper = function(i) {
return function(e) { alert(i); };
};
var i;
for (i = 0; i < nodes.length; i += 1) {
nodes[i].onclick = helper(i);
}
}
Each call to helper returns a function where the reference to "i" is bound to the closure for that helper call. Note the semantic distinction with code that doesn't use the helper, but just does this:
nodes[i].onclick = function() { alert(i); }
Here "i" again binds to a closure, but it's the closure associated with the call to add_the_handlers, so clicking on each node displays the same value, which is the number of nodes not the ordinal. That's the last value assigned to "i".
This question already has answers here:
JavaScript closure inside loops – simple practical example
(44 answers)
Closed 8 months ago.
I was writing a code that basically adds event listeners that call a function with the a fragment of their dom object's id, but every time I click an object with the listener It just gives me the same value no matter what object I click. Here's my code:
//add events
for (a=0; a<=tab_array.length-3; a++)
{
alert(a);
document.getElementById("mini_"+a).addEventListener("click",function(){open_tab(a)},false);
}
function open_tab(e)
{
//change across settings ect
alert("tab "+e+" clicked");
}
I realize it probably has something to do with pointers and that fact its using an anonymous function instead of directing passing a, but I just don't know what to do instead.
Your guess is correct. The behavior you see is because of your scope.
When your link is clicked javascript is passing the current value of a.
This value is tab_array.length-2 instead of the value a had during the loop run 0, 1 ....
To keep the value of a you have to create a new variable in a new scope (closure). E.g. e:
for (a=0; a<=tab_array.length-3; a++)
{
function(e){
document.getElementById("mini_"+e).addEventListener("click",function(){open_tab(e)},false);
}(a));
}
Another way would be to write a function which returns your handler inside its own scope:
//add events
for (a=0; a<=tab_array.length-3; a++)
{
alert(a);
document.getElementById("mini_"+a).addEventListener("click", open_tab(a) ,false);
}
function open_tab(e) {
return function() {
//change across settings ect
alert("tab "+e+" clicked");
}
}
See my fiddle or the Closure guide
Both of #jantimon's code samples are fine ways to solve this problem, but I'd like to suggest a third approach. Instead of a self-calling function expression or a function that returns a function, consider an ordinary named function:
for( var i = 0; i <= tab_array.length - 3; ++i ) {
setupTab( i );
}
function setupTab( i ) {
var element = document.getElementById( 'mini_' + i );
element.addEventListener( 'click', function() {
open_tab( i );
});
}
This is essentially the same code as the self-calling function, but with these advantages:
Familiarity. It's just an ordinary function call.
Shorter and simpler loop body.
With the self-calling function, the function parameter and the actual argument passed in are at opposite ends of the function (parameter at the beginning, argument at the end). A separate function avoids that.
These are just minor advantages, to be sure—any of these approaches will do the trick. But I do like the clarity of this method.
This question already has answers here:
do something when function executes Jquery
(2 answers)
Closed 9 years ago.
Is it possible to execute something every time a specific function runs without any knowledge about that function besides its name?
This would be similar to bind
var clicked = 0;
$('#foo').bind('click',function(){
clicked += 1;
alert(clicked);
});
So there, every time something with the ID foo is clicked, it will add 1 to the variable clicked so that I know how many times it has been clicked. What I want to do would be the equivalent of the following if it were correct syntax:
var fired = 0;
$('my_function').bind('run',function(){
fired += 1;
alert(fired);
});
I don't care if in any given situation you would be in, you would always be able to figure something out about the function and use that, I don't want work arounds, this is what I want for an answer:
How I can execute something everytime a specific function runs, just given the name of the function. If that is not possible, why not?
Try something like this:
var temp = my_function, fired = 0;
my_function = function() {
fired++;
temp.apply(this,arguments);
}
I think something like this may be the closest you can come:
function adjustFunctionToCount(f){
var count = 0;
function newF(){
count++;
f.apply(this, arguments);
}
newF.getCount = function(){ return count; };
return newF;
}
And so if you have
function handler(val){
console.log('called with val ' + val);
}
You could do
handler = adjustFunctionToCount(handler);
handler('a');
handler('b');
console.log(handler.getCount());
FIDDLE
And needless to say you could create your function inline
var handler = adjustFunctionToCount(function(val){ console.log('called with val ' + val); });
handler('a');
handler('b');
console.log(handler.getCount());
UPDATED FIDDLE
I'm pretty sure that's impossible in the general case.
Remember, functions are objects, really, and the name of a function is just a variable. Functions can exist without being assigned to a named variable, the variables can be out of your scope, or reassigned/swapped around. In any case, I know of no API that lets you hook onto a JS function call.
This may be of interest: Can I intercept a function called directly?
This is where event driven programming comes in - and jQuery makes it really easy to do.
var myFunction = function() {
//...
//...
//...
$(document).trigger('someEvent');
}
$(document).on('someEvent',function() {
//the function you would like to run every time myFunction is called
});
Try this:
var count = (function(){
var c = 0;
return function(){
alert(c++);
};
})();
$('#foo').click(count);
OR
$('#foo').bind('click', count);
When an Anonymous Function or a Variable that represents a Function is passed it is the same thing. You could make your own code that executes a Function like this:
function executeFun(func){
return func();
}
executeFun(count)
executeFun(function(){
/*everything happens in here. The Anonymous Function will be called
automatically because of the parameter next to the variable func above */
})
Although, that example is impractical it shows you what happens internally. Also, I solved your potential global scope variable problem with a Closure. For more on Closures visit https://developer.mozilla.org/en-US/docs/Web/JavaScript/Guide/Closures .
This question already has answers here:
Closed 11 years ago.
Possible Duplicate:
What do empty parentheses () after a function declaration do in javascript?
I am looking at some Javascript code and trying to figure out what }(); right after return num+10 means. Does that mean the function will get executed immediately? Where can I get more information about this.
function addToTen(num) {
return function() {
return num+10;
}();
}
addToTen(5); // 15
Thanks,
Venn.
Yes, but only if it's a function expression, which is different from a function declaration. A function declaration is how your first function is defined:
function foo(){
}
If you add () after this, you get a Syntax Error. If the function is defined as a function expression, adding a set of parenthesis immediately executes it. Functions are expressions whenever they are not defined as above, e.g.:
(function(){}());
var x = function(){}();
return function(){}();
Your actual example is just... odd, and pointless. It's almost a classic closure example, something like:
function addTo(x){
return function(y){
return x + y;
}
}
var addToTen = addTo(10);
addToTen(5); // 15;
but your actual example is equivalent to just:
function addToTen(num){
return num + 10;
}
and all the extra stuff is completely unnecessary.
Yes, it means the function object is evaluated.
Just like with any other function, you have two ways of looking at it:
var myFunction = function(val) {
return val + 1;
}
To return the function object, or send it somewhere else, I just say myFunction
If I wish to execute it, I say myFunction()
In this closure or decorator, whatever, that you've described above, rather than return the function object itself, you're returning the value of executing that function immediately, hence the () afterwards.
Yes, it's executed immediately, but the usage doesn't make any sense in this example.
Often used for anonymous functions creating a closure.
see Why do you need to invoke an anonymous function on the same line?
One place where I use it a lot:
(function($) {
// secure way to ensure no conflict between $ (jQuery)
// and another js-framework can happen
$...
})(jQuery);