how do functions work in javascript - javascript

i have a simple function called Range that creates an array of integers based on start, step and end value...
function Range (start, end, step) {
// default step is 1..
if (step === undefined ) step = 1;
// creating an array...
var arr = [], index = 0;
while(start <= end) {
arr[index] = start ;
index += 1;
start += step;
}
// simple function expressions
var getAll = function () {
return arr ;
};
var getOne = function(n) {
return arr[n] ;
};
// returns a unnamed function ..
return function(i) {
if (i === undefined) { return getAll() ;}
else {return getOne(i); }
}; // not an iife
}
so basically Range is a function which returns a unnamed function which again returns a named function expression declared in the function Range.. err.. i dont know.. something like that...
now the below code...
var first10 = Range (1,10) ; // no new ..() here, so no instance should be created.. only Range is called..
var first10Odd = Range(1,20,2) ; // and Range is called again..
alert(first10); // alerts - function(i) { ... }
alert(first10Odd); // alerts- function(i) { ... }
alert(first10()) ; // alerts - 1,2,3,...10
alert(first10Odd()); // alerts - 1,3,5,...19
alert(first10(0)); // alerts - 1
alert(first10Odd(9)); // alerts- 19
why do the alerts alert as specified in the comments??... i think Range is a just a function and not a object constructor and also no instance was created... shouldn't the local variables of function be destroyed as soon as the function is completed??
or is my logic wrong?? what is going on in the above code?? can anyone please explain....
i have made a fiddle of my code here..
sorry for asking this stupid question..

Welcome to the land of closures in Javascript. They can be very powerful and extremely useful once you understand them. But, if your prior experience is with languages that do not have them, they can feel a bit foreign at first.
Some answers/explanation:
Calling Range(x, y) returns a function that can then be called later.
Because that function that is returned is inside another function scope that has variables, a closure is created.
That closure stays alive (even though the outer function has finished executing) because there is a lasting reference to the inner function saved in your variables and that inner function has a reference to the local variables in the outer function. These references keep the closure from being garbage collected (so it stays alive).
That inner function can then reference the variables in the outer function, including the arguments originally passed to it.
This construct allows you to create these custom functions that have arguments pre-built into them.
The notion of this type of closure only exists in some languages. It does not exist in C++, for example.
When the function returned by calling Range(x,y) is itself executed later, it can use any of the variables that were originally in scope to it.
Each call to Range(x,y) causes a new closure to be created.
getAll and getOne are local variables in the outer function that are assigned a function. They access other local variables in the outer function. All of these are in the previously mentioned closure that is created each time Range() is called.
There is lots written about what a closure is (which you can Google and read), but I like to think of it as an execution context that contains everything that was in scope at the time a function is called (including all variables). Each time a function is called, such an execution context it created. Since everything in javascript is garbage collected and will only be freed/destroyed when there are no references left to it, this is true for this execution context too (e.g. closure). As long as something has a reference to it or something in it, then the execution context will stay alive and can be used by any code that might run into that execution context.
Line by line annotation:
// first10 is assigned the anonymous function that the call to Range()
// returned. That anonymous function has access to the original arguments
// passed to the Range(1,10) call and other local variables in that function.
var first10 = Range (1,10) ; // no new ..() here, so no instance should be created.. only Range is called..
// same as the call before, except this also includes the step argument
var first10Odd = Range(1,20,2) ; // and Range is called again..
// this makes sense because Range(1,10) returns a function so
// when you alert it's value, it tells you it's a function
alert(first10); // alerts - function(i) { ... }
alert(first10Odd); // alerts- function(i) { ... }
// When you execute the function in first10, it runs that function
// and the alert shows the return value from that function
// This particular function is set to return the entire array if nothing is passed
// to it
alert(first10()) ; // alerts - 1,2,3,...10
alert(first10Odd()); // alerts - 1,3,5,...19
// This particular function is set to return a specific index from the array
// if an argument is passed to it
alert(first10(0)); // alerts - 1
alert(first10Odd(9)); // alerts- 19
If you know how to use the javascript debugger, you can set a breakpoint on this line if (i === undefined) { return getAll() ;} in the inner function and you will be able to inspect all the variables that are in scope, including start, end and step from the outer function.
You may find this article useful reading as it encapsulates some of the ways that closures can be used with object declarations: http://javascript.crockford.com/private.html (not exactly what is being done here, but might help you understand them).

Welcome to javascript closures. Lets take line by line.
var first10 = Range(1,10);
var first10Odd = Range(1,20,2);
We know that Range is just a function. So, in these two lines we are just calling Range function with 2 and 3 arguments respectively.
Now, what happens when you call a function. The obvious answer is, the body of the function gets executed. What do we have in the body of the function.
if (step === undefined ) step = 1;
var arr = [], index = 0;
while(start <= end) {
arr[index] = start ;
index += 1;
start += step;
}
I hope that the above seen lines are pretty obvious and you don't have any problems with them.
var getAll = function () {
return arr;
};
What does this line do? It creates a function at run time. Why runtime? Lets see an example.
<script>
func1();
var func1 = function() {
alert("Hi");
}
</script>
<script>
func1();
function func1() {
alert("Hi");
}
</script>
If you use the first script block, it will throw error. Why? You are calling a function which hasn't been defined yet. The second case, you are defining the function during javascript parsing time itself. The type of function which was created in the first case is called anonymous function. Let us get back to getAll. Now we know that getAll is simply a variable which points to an anonymous function, lets look at what it does. It returns arr. How does it have access to arr? It is declared outside the function and so it still has access to it. Same case with
var getOne = function(n) {
return arr[n] ;
};
Now the very important part,
return function(i) {
if (i === undefined) {
return getAll();
} else {
return getOne(i);
}
};
What does it do? It returns a function. To be precise, it returns an anonymous function. Whenever Range is called, it creates a new anonymous function, which accepts one parameter and returns it. So, now what do first10 and first10Odd have? Yes. You are right, they have functions. I hope that explains
alert(first10); // alerts - function(i) { ... }
alert(first10Odd); // alerts - function(i) { ... }
Let us examine both the functions. When first10 is called with nothing, I mean, first10(), the parameter i takes the value undefined. So, we are actually making a call to the anonymous function with no parameters and it is supposed to return getAll(). If you remember, first10 was created with Range(1,10);. So, the arr will now have [1, 2, 3, 4, 5, 6, 7, 8, 9, 10].
You might ask, when we return from the function, wont the variables declared inside the function go out of scope. The answer is Yes and No. Yes, when you simply return a value. No, when you return a function. When you return a function, the state of the variables will be maintained. This property is called closures. That is why it returns
[1, 2, 3, 4, 5, 6, 7, 8, 9, 10] for alert(first10())
[1, 3, 5, 7, 9, 11, 13, 15, 17, 19] for alert(first10Odd())
1 for alert(first10(0))
19 for alert(first10Odd(9))
Please read more about Closure here https://developer.mozilla.org/en-US/docs/Web/JavaScript/Guide/Closures

Related

why return a function inside another function in javascript? is there any advantages? [duplicate]

I'm trying my hardest to wrap my head around JavaScript closures.
I get that by returning an inner function, it will have access to any variable defined in its immediate parent.
Where would this be useful to me? Perhaps I haven't quite got my head around it yet. Most of the examples I have seen online don't provide any real world code, just vague examples.
Can someone show me a real world use of a closure?
Is this one, for example?
var warnUser = function (msg) {
var calledCount = 0;
return function() {
calledCount++;
alert(msg + '\nYou have been warned ' + calledCount + ' times.');
};
};
var warnForTamper = warnUser('You can not tamper with our HTML.');
warnForTamper();
warnForTamper();
Suppose, you want to count the number of times user clicked a button on a webpage.
For this, you are triggering a function on onclick event of button to update the count of the variable
<button onclick="updateClickCount()">click me</button>
Now there could be many approaches like:
You could use a global variable, and a function to increase the counter:
var counter = 0;
function updateClickCount() {
++counter;
// Do something with counter
}
But, the pitfall is that any script on the page can change the counter, without calling updateClickCount().
Now, you might be thinking of declaring the variable inside the function:
function updateClickCount() {
var counter = 0;
++counter;
// Do something with counter
}
But, hey! Every time updateClickCount() function is called, the counter is set to 1 again.
Thinking about nested functions?
Nested functions have access to the scope "above" them.
In this example, the inner function updateClickCount() has access to the counter variable in the parent function countWrapper():
function countWrapper() {
var counter = 0;
function updateClickCount() {
++counter;
// Do something with counter
}
updateClickCount();
return counter;
}
This could have solved the counter dilemma, if you could reach the updateClickCount() function from the outside and you also need to find a way to execute counter = 0 only once not everytime.
Closure to the rescue! (self-invoking function):
var updateClickCount = (function(){
var counter = 0;
return function(){
++counter;
// Do something with counter
}
})();
The self-invoking function only runs once. It sets the counter to zero (0), and returns a function expression.
This way updateClickCount becomes a function. The "wonderful" part is that it can access the counter in the parent scope.
This is called a JavaScript closure. It makes it possible for a function to have "private" variables.
The counter is protected by the scope of the anonymous function, and can only be changed using the updateClickCount() function!
A more lively example on closures
<script>
var updateClickCount = (function(){
var counter = 0;
return function(){
++counter;
document.getElementById("spnCount").innerHTML = counter;
}
})();
</script>
<html>
<button onclick="updateClickCount()">click me</button>
<div> you've clicked
<span id="spnCount"> 0 </span> times!
</div>
</html>
Reference: JavaScript Closures
I've used closures to do things like:
a = (function () {
var privatefunction = function () {
alert('hello');
}
return {
publicfunction : function () {
privatefunction();
}
}
})();
As you can see there, a is now an object, with a method publicfunction ( a.publicfunction() ) which calls privatefunction, which only exists inside the closure. You can not call privatefunction directly (i.e. a.privatefunction() ), just publicfunction().
It's a minimal example, but maybe you can see uses to it? We used this to enforce public/private methods.
The example you give is an excellent one. Closures are an abstraction mechanism that allow you to separate concerns very cleanly. Your example is a case of separating instrumentation (counting calls) from semantics (an error-reporting API). Other uses include:
Passing parameterised behaviour into an algorithm (classic higher-order programming):
function proximity_sort(arr, midpoint) {
arr.sort(function(a, b) { a -= midpoint; b -= midpoint; return a*a - b*b; });
}
Simulating object oriented programming:
function counter() {
var a = 0;
return {
inc: function() { ++a; },
dec: function() { --a; },
get: function() { return a; },
reset: function() { a = 0; }
}
}
Implementing exotic flow control, such as jQuery's Event handling and AJAX APIs.
JavaScript closures can be used to implement throttle and debounce functionality in your application.
Throttling
Throttling puts a limit on as a maximum number of times a function can be called over time. As in "execute this function at most once every 100 milliseconds."
Code:
const throttle = (func, limit) => {
let isThrottling
return function() {
const args = arguments
const context = this
if (!isThrottling) {
func.apply(context, args)
isThrottling = true
setTimeout(() => isThrottling = false, limit)
}
}
}
Debouncing
Debouncing puts a limit on a function not be called again until a certain amount of time has passed without it being called. As in "execute this function only if 100 milliseconds have passed without it being called."
Code:
const debounce = (func, delay) => {
let debouncing
return function() {
const context = this
const args = arguments
clearTimeout(debouncing)
debouncing = setTimeout(() => func.apply(context, args), delay)
}
}
As you can see closures helped in implementing two beautiful features which every web application should have to provide smooth UI experience functionality.
Yes, that is a good example of a useful closure. The call to warnUser creates the calledCount variable in its scope and returns an anonymous function which is stored in the warnForTamper variable. Because there is still a closure making use of the calledCount variable, it isn't deleted upon the function's exit, so each call to the warnForTamper() will increase the scoped variable and alert the value.
The most common issue I see on Stack Overflow is where someone wants to "delay" use of a variable that is increased upon each loop, but because the variable is scoped then each reference to the variable would be after the loop has ended, resulting in the end state of the variable:
for (var i = 0; i < someVar.length; i++)
window.setTimeout(function () {
alert("Value of i was "+i+" when this timer was set" )
}, 10000);
This would result in every alert showing the same value of i, the value it was increased to when the loop ended. The solution is to create a new closure, a separate scope for the variable. This can be done using an instantly executed anonymous function, which receives the variable and stores its state as an argument:
for (var i = 0; i < someVar.length; i++)
(function (i) {
window.setTimeout(function () {
alert("Value of i was " + i + " when this timer was set")
}, 10000);
})(i);
In the JavaScript (or any ECMAScript) language, in particular, closures are useful in hiding the implementation of functionality while still revealing the interface.
For example, imagine you are writing a class of date utility methods and you want to allow users to look up weekday names by index, but you don't want them to be able to modify the array of names you use under the hood.
var dateUtil = {
weekdayShort: (function() {
var days = ['Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat', 'Sun'];
return function(x) {
if ((x != parseInt(x)) || (x < 1) || (x > 7)) {
throw new Error("invalid weekday number");
}
return days[x - 1];
};
}())
};
Note that the days array could simply be stored as a property of the dateUtil object, but then it would be visible to users of the script and they could even change it if they wanted, without even needing your source code. However, since it's enclosed by the anonymous function which returns the date lookup function it is only accessible by the lookup function so it is now tamperproof.
There is a section on Practical Closures at the Mozilla Developer Network.
If you're comfortable with the concept of instantiating a class in the object-oriented sense (i.e. to create an object of that class) then you're close to understanding closures.
Think of it this way: when you instantiate two Person objects you know that the class member variable "Name" is not shared between instances; each object has its own 'copy'. Similarly, when you create a closure, the free variable ('calledCount' in your example above) is bound to the 'instance' of the function.
I think your conceptual leap is slightly hampered by the fact that every function/closure returned by the warnUser function (aside: that's a higher-order function) closure binds 'calledCount' with the same initial value (0), whereas often when creating closures it is more useful to pass different initializers into the higher-order function, much like passing different values to the constructor of a class.
So, suppose when 'calledCount' reaches a certain value you want to end the user's session; you might want different values for that depending on whether the request comes in from the local network or the big bad internet (yes, it's a contrived example). To achieve this, you could pass different initial values for calledCount into warnUser (i.e. -3, or 0?).
Part of the problem with the literature is the nomenclature used to describe them ("lexical scope", "free variables"). Don't let it fool you, closures are more simple than would appear... prima facie ;-)
Here, I have a greeting that I want to say several times. If I create a closure, I can simply call that function to record the greeting. If I don't create the closure, I have to pass my name in every single time.
Without a closure (https://jsfiddle.net/lukeschlangen/pw61qrow/3/):
function greeting(firstName, lastName) {
var message = "Hello " + firstName + " " + lastName + "!";
console.log(message);
}
greeting("Billy", "Bob");
greeting("Billy", "Bob");
greeting("Billy", "Bob");
greeting("Luke", "Schlangen");
greeting("Luke", "Schlangen");
greeting("Luke", "Schlangen");
With a closure (https://jsfiddle.net/lukeschlangen/Lb5cfve9/3/):
function greeting(firstName, lastName) {
var message = "Hello " + firstName + " " + lastName + "!";
return function() {
console.log(message);
}
}
var greetingBilly = greeting("Billy", "Bob");
var greetingLuke = greeting("Luke", "Schlangen");
greetingBilly();
greetingBilly();
greetingBilly();
greetingLuke();
greetingLuke();
greetingLuke();
Another common use for closures is to bind this in a method to a specific object, allowing it to be called elsewhere (such as as an event handler).
function bind(obj, method) {
if (typeof method == 'string') {
method = obj[method];
}
return function () {
method.apply(obj, arguments);
}
}
...
document.body.addEventListener('mousemove', bind(watcher, 'follow'), true);
Whenever a mousemove event fires, watcher.follow(evt) is called.
Closures are also an essential part of higher-order functions, allowing the very common pattern of rewriting multiple similar functions as a single higher order function by parameterizing the dissimilar portions. As an abstract example,
foo_a = function (...) {A a B}
foo_b = function (...) {A b B}
foo_c = function (...) {A c B}
becomes
fooer = function (x) {
return function (...) {A x B}
}
where A and B aren't syntactical units but source code strings (not string literals).
See "Streamlining my javascript with a function" for a concrete example.
Here I have one simple example of the closure concept which we can use for in our E-commerce site or many others as well.
I am adding my JSFiddle link with the example. It contains a small product list of three items and one cart counter.
JSFiddle
// Counter closure implemented function;
var CartCouter = function(){
var counter = 0;
function changeCounter(val){
counter += val
}
return {
increment: function(){
changeCounter(1);
},
decrement: function(){
changeCounter(-1);
},
value: function(){
return counter;
}
}
}
var cartCount = CartCouter();
function updateCart() {
document.getElementById('cartcount').innerHTML = cartCount.value();
}
var productlist = document.getElementsByClassName('item');
for(var i = 0; i< productlist.length; i++){
productlist[i].addEventListener('click', function(){
if(this.className.indexOf('selected') < 0){
this.className += " selected";
cartCount.increment();
updateCart();
}
else{
this.className = this.className.replace("selected", "");
cartCount.decrement();
updateCart();
}
})
}
.productslist{
padding: 10px;
}
ul li{
display: inline-block;
padding: 5px;
border: 1px solid #DDD;
text-align: center;
width: 25%;
cursor: pointer;
}
.selected{
background-color: #7CFEF0;
color: #333;
}
.cartdiv{
position: relative;
float: right;
padding: 5px;
box-sizing: border-box;
border: 1px solid #F1F1F1;
}
<div>
<h3>
Practical use of a JavaScript closure concept/private variable.
</h3>
<div class="cartdiv">
<span id="cartcount">0</span>
</div>
<div class="productslist">
<ul>
<li class="item">Product 1</li>
<li class="item">Product 2</li>
<li class="item">Product 3</li>
</ul>
</div>
</div>
Use of Closures:
Closures are one of the most powerful features of JavaScript. JavaScript allows for the nesting of functions and grants the inner function full access to all the variables and functions defined inside the outer function (and all other variables and functions that the outer function has access to). However, the outer function does not have access to the variables and functions defined inside the inner function.
This provides a sort of security for the variables of the inner function. Also, since the inner function has access to the scope of the outer function, the variables and functions defined in the outer function will live longer than the outer function itself, if the inner function manages to survive beyond the life of the outer function. A closure is created when the inner function is somehow made available to any scope outside the outer function.
Example:
<script>
var createPet = function(name) {
var sex;
return {
setName: function(newName) {
name = newName;
},
getName: function() {
return name;
},
getSex: function() {
return sex;
},
setSex: function(newSex) {
if(typeof newSex == "string" && (newSex.toLowerCase() == "male" || newSex.toLowerCase() == "female")) {
sex = newSex;
}
}
}
}
var pet = createPet("Vivie");
console.log(pet.getName()); // Vivie
console.log(pet.setName("Oliver"));
console.log(pet.setSex("male"));
console.log(pet.getSex()); // male
console.log(pet.getName()); // Oliver
</script>
In the code above, the name variable of the outer function is accessible to the inner functions, and there is no other way to access the inner variables except through the inner functions. The inner variables of the inner function act as safe stores for the inner functions. They hold "persistent", yet secure, data for the inner functions to work with. The functions do not even have to be assigned to a variable, or have a name.
read here for detail.
Explaining the practical use for a closure in JavaScript
When we create a function inside another function, we are creating a closure. Closures are powerful because they are capable of reading and manipulating the data of its outer functions. Whenever a function is invoked, a new scope is created for that call. The local variable declared inside the function belong to that scope and they can only be accessed from that function. When the function has finished the execution, the scope is usually destroyed.
A simple example of such function is this:
function buildName(name) {
const greeting = "Hello, " + name;
return greeting;
}
In above example, the function buildName() declares a local variable greeting and returns it. Every function call creates a new scope with a new local variable. After the function is done executing, we have no way to refer to that scope again, so it’s garbage collected.
But how about when we have a link to that scope?
Let’s look at the next function:
function buildName(name) {
const greeting = "Hello, " + name + " Welcome ";
const sayName = function() {
console.log(greeting);
};
return sayName;
}
const sayMyName = buildName("Mandeep");
sayMyName(); // Hello, Mandeep Welcome
The function sayName() from this example is a closure. The sayName() function has its own local scope (with variable welcome) and has also access to the outer (enclosing) function’s scope. In this case, the variable greeting from buildName().
After the execution of buildName is done, the scope is not destroyed in this case. The sayMyName() function still has access to it, so it won’t be garbage collected. However, there is no other way of accessing data from the outer scope except the closure. The closure serves as the gateway between the global context and the outer scope.
The JavaScript module pattern uses closures. Its nice pattern allows you to have something alike "public" and "private" variables.
var myNamespace = (function () {
var myPrivateVar, myPrivateMethod;
// A private counter variable
myPrivateVar = 0;
// A private function which logs any arguments
myPrivateMethod = function(foo) {
console.log(foo);
};
return {
// A public variable
myPublicVar: "foo",
// A public function utilizing privates
myPublicFunction: function(bar) {
// Increment our private counter
myPrivateVar++;
// Call our private method using bar
myPrivateMethod(bar);
}
};
})();
I like Mozilla's function factory example.
function makeAdder(x) {
return function(y) {
return x + y;
};
}
var addFive = makeAdder(5);
console.assert(addFive(2) === 7);
console.assert(addFive(-5) === 0);
This thread has helped me immensely in gaining a better understanding of how closures work.
I've since done some experimentation of my own and came up with this fairly simple code which may help some other people see how closures can be used in a practical way and how to use the closure at different levels to maintain variables similar to static and/or global variables without risk of them getting overwritten or confused with global variables.
This keeps track of button clicks, both at a local level for each individual button and a global level, counting every button click, contributing towards a single figure. Note I haven't used any global variables to do this, which is kind of the point of the exercise - having a handler that can be applied to any button that also contributes to something globally.
Please experts, do let me know if I've committed any bad practices here! I'm still learning this stuff myself.
<!doctype html>
<html>
<head>
<meta charset="utf-8">
<title>Closures on button presses</title>
<script type="text/javascript">
window.addEventListener("load" , function () {
/*
Grab the function from the first closure,
and assign to a temporary variable
this will set the totalButtonCount variable
that is used to count the total of all button clicks
*/
var buttonHandler = buttonsCount();
/*
Using the result from the first closure (a function is returned)
assign and run the sub closure that carries the
individual variable for button count and assign to the click handlers
*/
document.getElementById("button1").addEventListener("click" , buttonHandler() );
document.getElementById("button2").addEventListener("click" , buttonHandler() );
document.getElementById("button3").addEventListener("click" , buttonHandler() );
// Now that buttonHandler has served its purpose it can be deleted if needs be
buttonHandler = null;
});
function buttonsCount() {
/*
First closure level
- totalButtonCount acts as a sort of global counter to count any button presses
*/
var totalButtonCount = 0;
return function () {
// Second closure level
var myButtonCount = 0;
return function (event) {
// Actual function that is called on the button click
event.preventDefault();
/*
Increment the button counts.
myButtonCount only exists in the scope that is
applied to each event handler and therefore acts
to count each button individually, whereas because
of the first closure totalButtonCount exists at
the scope just outside, it maintains a sort
of static or global variable state
*/
totalButtonCount++;
myButtonCount++;
/*
Do something with the values ... fairly pointless
but it shows that each button contributes to both
its own variable and the outer variable in the
first closure
*/
console.log("Total button clicks: "+totalButtonCount);
console.log("This button count: "+myButtonCount);
}
}
}
</script>
</head>
<body>
Button 1
Button 2
Button 3
</body>
</html>
There are various use cases of closures.Here, I am going to explain most important usage of Closure concept.
Closure can be used to create private methods and variables just like an object-oriented language like java, c++ and so on. Once you implemented private methods and variables, your variables defined inside a function won't be accessible by window object. This helps in data hiding and data security.
const privateClass = () => {
let name = "sundar";
function setName(changeName) {
name = changeName;
}
function getName() {
return name;
}
return {
setName: setName,
getName: getName,
};
};
let javaLikeObject = privateClass(); \\ similar to new Class() in OOPS.
console.log(javaLikeObject.getName()); \\this will give sundar
javaLikeObject.setName("suresh");
console.log(javaLikeObject.getName()); \\this will give suresh
Another real-life example of closure :
Create index.html:
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Program with Javascript</title>
</head>
<body>
<p id="first"></p>
<p id="second"></p>
<button onclick="applyingConcepts()">Click</button>
<script src="./index.js"></script>
</body>
</html>
2)In index.js:
let count = 0;
return () => {
document.getElementById("first").innerHTML = count++;
};
})();
In this example, when you click a button, then your count will be updated on p#id.
Note: You might be wondering what's special in this code. When you inspect, you will notice that you can't change the value of count using the window object. This means you have declared private variable count so this prevents your states from being spoiled by the client.
I wrote an article a while back about how closures can be used to simplify event-handling code. It compares ASP.NET event handling to client-side jQuery.
http://www.hackification.com/2009/02/20/closures-simplify-event-handling-code/
Much of the code we write in front-end JavaScript is event-based — we define some behavior, then attach it to an event that is triggered by the user (such as a click or a keypress). Our code is generally attached as a callback: a single function which is executed in response to the event.
size12, size14, and size16 are now functions which will resize the body text to 12, 14, and 16 pixels, respectively. We can attach them to buttons (in this case links) as follows:
function makeSizer(size) {
return function() {
document.body.style.fontSize = size + 'px';
};
}
var size12 = makeSizer(12);
var size14 = makeSizer(14);
var size16 = makeSizer(16);
document.getElementById('size-12').onclick = size12;
document.getElementById('size-14').onclick = size14;
document.getElementById('size-16').onclick = size16;
Fiddle
Closures are a useful way to create generators, a sequence incremented on-demand:
var foobar = function(i){var count = count || i; return function(){return ++count;}}
baz = foobar(1);
console.log("first call: " + baz()); //2
console.log("second call: " + baz()); //3
The differences are summarized as follows:
Anonymous functions Defined functions
Cannot be used as a method Can be used as a method of an object
Exists only in the scope in which it is defined Exists within the object it is defined in
Can only be called in the scope in which it is defined Can be called at any point in the code
Can be reassigned a new value or deleted Cannot be deleted or changed
References
AS3 Fundamentals: Functions
I'm trying to learn closures and I think the example that I have created is a practical use case. You can run a snippet and see the result in the console.
We have two separate users who have separate data. Each of them can see the actual state and update it.
function createUserWarningData(user) {
const data = {
name: user,
numberOfWarnings: 0,
};
function addWarning() {
data.numberOfWarnings = data.numberOfWarnings + 1;
}
function getUserData() {
console.log(data);
return data;
}
return {
getUserData: getUserData,
addWarning: addWarning,
};
}
const user1 = createUserWarningData("Thomas");
const user2 = createUserWarningData("Alex");
//USER 1
user1.getUserData(); // Returning data user object
user1.addWarning(); // Add one warning to specific user
user1.getUserData(); // Returning data user object
//USER2
user2.getUserData(); // Returning data user object
user2.addWarning(); // Add one warning to specific user
user2.addWarning(); // Add one warning to specific user
user2.getUserData(); // Returning data user object
Reference: Practical usage of closures
In practice, closures may create elegant designs, allowing customization of various calculations, deferred calls, callbacks, creating encapsulated scope, etc.
An example is the sort method of arrays which accepts the sort condition function as an argument:
[1, 2, 3].sort(function (a, b) {
... // Sort conditions
});
Mapping functionals as the map method of arrays which maps a new array by the condition of the functional argument:
[1, 2, 3].map(function (element) {
return element * 2;
}); // [2, 4, 6]
Often it is convenient to implement search functions with using functional arguments defining almost unlimited conditions for search:
someCollection.find(function (element) {
return element.someProperty == 'searchCondition';
});
Also, we may note applying functionals as, for example, a forEach method which applies a function to an array of elements:
[1, 2, 3].forEach(function (element) {
if (element % 2 != 0) {
alert(element);
}
}); // 1, 3
A function is applied to arguments (to a list of arguments — in apply, and to positioned arguments — in call):
(function () {
alert([].join.call(arguments, ';')); // 1;2;3
}).apply(this, [1, 2, 3]);
Deferred calls:
var a = 10;
setTimeout(function () {
alert(a); // 10, after one second
}, 1000);
Callback functions:
var x = 10;
// Only for example
xmlHttpRequestObject.onreadystatechange = function () {
// Callback, which will be called deferral ,
// when data will be ready;
// variable "x" here is available,
// regardless that context in which,
// it was created already finished
alert(x); // 10
};
Creation of an encapsulated scope for the purpose of hiding auxiliary objects:
var foo = {};
(function (object) {
var x = 10;
object.getX = function _getX() {
return x;
};
})(foo);
alert(foo.getX()); // Get closured "x" – 10
In the given sample, the value of the enclosed variable 'counter' is protected and can be altered only using the given functions (increment, decrement). Because it is in a closure,
var MyCounter = function (){
var counter = 0;
return {
increment:function () {return counter += 1;},
decrement:function () {return counter -= 1;},
get:function () {return counter;}
};
};
var x = MyCounter();
// Or
var y = MyCounter();
alert(x.get()); // 0
alert(x.increment()); // 1
alert(x.increment()); // 2
alert(y.increment()); // 1
alert(x.get()); // x is still 2
Everyone has explained the practical use cases of closure: the definition and a couple of examples.
I want to contribute a list of use cases of Closures:
suppose you want to count no of times a button is clicked; Closure is the best choice.
Throttling and Debounce
Currying
Memorize
Maintaining state in the async world
Functions like once
setTimeouts
Iterators

Returning a value inside an if clause in javascript

_editor: function () {
//retrieve all the editors on the current page
var editors = window.tinymce.editors;
var container = this.element;
//pick one that's associated with current container
$(editors).each(function (i, ed) {
if (ed.id == container.id) {
return ed; // even if this is invoked,
}
});
// undefined is returned
}
I had to change the above code to
_editor: function () {
//retrieve all the editors on the current page
var editors = window.tinymce.editors;
var container = this.element;
var editor;
$(editors).each(function (i, ed) {
if (ed.id == container.id) {
editor = ed; // do not return yet. Store it.
}
});
return editor; // return here
}
I assume this is because of JavaScript's scope characteristics. Could someone explain 1) if this is only inherent in JavaScript 2) what exactly is going on in each functional scope in the above code?
Thank you.
In the first case, you are returning a value from that anonymous function passed to $(editors).each, not the outer function. In the second case you are returning from the outer function.
This is how it works with pretty much any language that allows nested functions. return only returns from the innermost function.
The issue is that you have nested functions. You have the function assigned to the _editor property, and within that you have a function that's being invoked by $.each(). The return statement returns from the closest containing function, so in the first example it's returning from the $.each() iteration function, not the _editor function.
$.each() uses the return value of the iteration function to determine whether to continue looping -- if the function returns false, it stops at that element (similar to using the break; statement in a for or while loop).
Could someone explain 1) if this is only inherent in JavaScript 2) what exactly is going on in each functional scope in the above code?
The code is returning from the function passed to .each(), so it doesn't impact the enclosing function.
You can use $.grep for a cleaner solution.
_editor: function () {
//retrieve all the editors on the current page
var editors = window.tinymce.editors;
var container = this.element;
return $.grep(editors, function (ed, i) {
return ed.id == container.id;
})[0];
}
This is basically a filter. The result will be the items in the collection where you returned a truthy value. And so we just return the first truthy result (index 0 of the result).
It returns from the function called by each:
$(editors).each(function (i, ed) { // <---
if (ed.id == container.id) { |
return ed; // <--- this exits this --
is [this] only inherent in JavaScript[?]
No, many languages which use anonymous functions, also called lambdas, operate like this. A couple of examples are C# and ruby. Calling return exits themselves, rather than the functions they are invoked in.
what exactly is going on in each functional scope in the above code?
$(editors).each(function (i, ed) {
if (ed.id == container.id) {
editor = ed; // do not return yet. Store it.
}
});
The function body is called once for each element ed in $(editors). When the loop exits, the last value for which ed.id == container.id is then stored in editor. The second argument i is the index (0,1,2,3,...) incremented in each iteration.

Identify the pattern of this javascript function

this is a brief pattern of a javascript function which I am not able to understand.
this is as seen here:
https://github.com/g13n/ua.js/blob/master/src/ua.js.
Note: This an edited version as per HugoT's response to my original question's answer.
function D(arg) {
return function () {
return arg > 10; //arg is captured in this function's closure
}
};
object = {
x: D(11),
y: D(9),
z: D(12)
};
SO how does this structure work?
I can see the return is an object.
But I cant put the things together.
Is this a closure pattern?
Can anyone explain the flow?
Yes this is a closure pattern. Any arguments passed to D are captured in the closures of the function returned from D. However what you have written is not the same as in the code you linked.
This is the important part of the code you linked simplified
function D(arg) {
return function () {
return arg > 10; //arg is captured in this function's closure
}
};
object = {
x: D(11),
y: D(9),
z: D(12)
};
The values 11, 9 and 12 will be captured in the functions object.x, object.y and object.z.
Thus object.x() will return true while object.y will return false because 9 > 10 is false. object.z() will return true because 12 > 10
Let's break down ua.js to see what's going on. The outermost layer of the onion is an anonymous function:
var UA = (function (window, navigator)
{
/* anonymous function contents */
}(window, navigator));
So UA is set to the return value of this anonymous function. So what does the anonymous function do? It sets a variable ua.
var ua = (window.navigator && navigator.userAgent) || "";
It defines a function detect which returns an anonymous function which tests the contents of ua against pattern.
function detect(pattern) {
return function () {
return (pattern).test(ua);
};
}
Note that calling detect(/something/) does not return the value of (/something/).test(ua). It simply returns a closure that will perform the test on demand.
Now we hit the return value of our outer anonymous function, which looks like this (I've chopped out the comments):
return { isChrome: detect(/webkit\W.*(chrome|chromium)\W/i),
isFirefox: detect(/mozilla.*\Wfirefox\W/i),
isGecko: detect(/mozilla(?!.*webkit).*\Wgecko\W/i),
...
whoami: function () {
return ua;
} }
This is returning an instance of Object which contains a number of functions (isChrome etc), and those functions are the closures created by calls to detect(). This means that the execution of those (pattern).test(ua) checks are deferred until someone actually calls UA.isChrome() and so on.
You could imagine another approach where all the tests are performed up front, and UA becomes an Object containing a set of flags. This would have had the (probably fairly tiny) overhead of executing pattern matches that you as the developer are not interested in.

Unexpected behavior with closures: callback holds the last value

I'll get to the point: I have this loop:
for (var i = 1; i <= toSchedule; i++) {
when = trackWrapper.lastPlay +
(trackDuration +
(looper.timeInterval - trackDuration));
track.play(true, when);
trackWrapper.lastPlay = when;
}
The play method has this inside the body:
[...]
// Here when is a different value for each call (verified)
// Many calls of the play method are performed before the returned function below is run as a callback
function playingCallback(myWhen){
return function(buffers){
// Here myWhen will always be equal to the value of the last call occurred BEFORE the first callback execution
console.log("myWhen = "+myWhen);
[...]
};
};
var realCallback = playingCallback(when);
track.scheduled.push(when);
track.recorder.getBuffer(realCallback);
So, for example:
play(true, 1);
play(true, 2);
play(true, 3);
// Wait for it...
myWhen = 3;
myWhen = 3;
myWhen = 3;
Now: I've read about closures, I've read about the "infamous loop problem", I've read tens of answers here on StackOverflow but I couldn't figure this out. It's the second time I have this kind of problem with callbacks so, at this point, I guess I haven't completely understood what is going on.
Could you please explain to me what is supposed to be wrong with the code above? Thank you in advance.
Generally you should understand the following rule: A clousure will have access to its "surrounding scope", even after the scope has been exited. But it will be the state of the scope at execution time and not(!) at creation time of the closure
If you create a closure inside a loop, it will have access to the loop variable. But the loop will most likely already have ended. So the loop variable will hold the value of its last loop.
So if your closure is a callback you should create a copy of your relevant scope variable(s) at creation time and use this copy at execution time. You can do this (for example) by creating an inner closure from an immediately executing anonymous function
function myOuterScope(count) {
for(i=0; i<count; i++) {
setTimeout((function(local_i) {
// this function will be immediately executed. local_i is a copy of i at creation time
return function() {
// this is the function that will be called as a callback to setTimeout
// use local_i here, and it will be 0, 1, 2 instead of 3, 3, 3
}
})(i)
, 1000);
}
}
myOuterScope(3);

Reassign variables stored in closure using a callback or global function

EDIT
Let me get more to the point. I'm trying to create a psuedo promise implementation. The idea here being that I have a callback that won't be executed until an asynchronous call is received. So I'm simply queueing up all the calls to this function until the time at which it's notified that it can be executed. The queue is emptied and any further call to the function is SUPPOSED to execute immediately, but for some reason, the function is still queueing. This is because, for whatever reason, my redefinition of the runner function is not working correctly. The code below was my sleep deprived, frustrated version of every thought that went through my head. Here's the actual code:
function Promise(callback){
var queue = []
, callback = callback
, runner = function(){
queue.push({
context: this,
args: Array.prototype.slice.call(arguments, 0)
});
}
;//var
runner.exec = function(){
for(var i = 0, ilen = queue.length; i < ilen; i++){
var q = queue[i];
callback.apply(q.context, q.args);
}
runner = callback;
};
return runner;
}
test = Promise(function(){
$('<div/>').appendTo('#output').html(Array.prototype.slice.call(arguments,0).toString());
});
test(1,2);
test(3,4);
test.exec();
test(5,6);​
http://jsfiddle.net/a7gaR/
I'm banging my head against the wall with this one. I'm trying to reassign variables in a function from a call outside the function itself (ideally by passing a reassignment function as a callback). In the example I posted on jsfiddle, I made a global function that, in theory, has a reference to the variables contained within its parent function. Upon calling that external function, I expect it to reassign the values that the other function is using. It doesn't seem to work this way.
window.test = function temp() {
var val = 7,
func = function() {
return val;
};
window.change = function() {
window.test.val = 555555;
$('<div>Changing ' + val + ' to ' + window.test.val +
'</div>').appendTo($output);
val = window.test.val;
temp.val = window.test.val;
func = function() {
return 'Why isn\'t this working?';
}
}
return func();
}
var $output = $('#output');
$('<div/>').appendTo($output).html('::' + test() + '::');
window.change();
$('<div/>').appendTo($output).html('::' + test() + '::');
http://jsfiddle.net/YhyMK/
The second time you call test you're creating a new local variable called func and defining a new window.change that closes over that new variable. The changes you made to the original func by calling the original window.change are not relevant in the second call.
Also note that the following line:
window.test.val = 555555;
...does not modify/refer to the val variable in the outer function. window.test.val refers to a property named val on the test object (which happens to be a function), not any local variable.
You are trying to refer to a local variable in a function with the syntax func.varname. That won't work, that's not the way local variables work.
I finally created a function that would perform this operation. The gist for it is here: https://gist.github.com/2586972.
It works like this...
You make a call to Defer passing the callback whose functionality you'd like to delay:
var deferredCB = Defer(function(){ console.log(this,arguments) };
deferredCB will now store all of the arguments you pass allowing them to be executed at some later date:
defferedCB(1);
defferedCB(2);
Now, when you're ready to perform the operation, you simply "execute" deferredCB:
defferedCB.exec();
Which results in:
// window, 1
// window, 2
All future calls to deferredCB will be executed immediately. And now that I'm thinking about it, I'll probably do a rewrite to allow you to reset deferredCB to it's pre-executed state (storing all the arguments again).
The key to making it work was having a wrapper function. Javascript simply won't let you reassign a function while it's being executed.
TADA!!!

Categories