Closures Questions Javascript
Q1. What will the code print?
let count = 0;
(function printCount() {
if (count === 0) {
let count = 1;
console.log(count);
}
console.log(count);
})();
?
Answer
let count = 0;
(function printCount() {
if (count === 0) {
let count = 1;
console.log(count); // 1
}
console.log(count); // 0
})();
Q2. Write a function that would allow you to do as in the following snippet
var addSix = createBase(6);
addSix(10); // prints 16
addSix(21); // prints 27
?
Answer
function createBase(num) {
return function (a) {
console.log( num + a );
}
}
Q3. Time optimization using Closure
function find(index) {
let a = [];
for (let i = 0 ; i < 1000000; i++) {
a[i] = i*i;
}
console.log(a[index]);
}
console.time("6");
find(6);
console.timeEnd("6");
console.time("12");
find(12);
console.timeEnd("12");
?
Answer
function find() {
let a = [];
for (let i = 0 ; i < 1000000 ; i++) {
a[i] = i * i;
}
return function (index) {
console.log(a[index]);
};
}
const closure = find();
console.time("6");
closure(6);
console.timeEnd("6");
console.time("12");
closure(12);
console.timeEnd("12");
Q4. Block scope & setTimeout with closure Output
function a() {
for (var i = 0 ; i < 3 ; i++) {
setTimeout(function log() {
console.log(i); // What is logged?
}, 1000);
}
}
a();
?
Answer
- // ans: 3, 3, 3
- This is because of the functional scope of Var Javascript
- How can this be fixed?
- Use Let Javascript as it is block scoped
- Go to source & review the followup questions
Followup 1: how will you print // 0, 1, 2
- We can use
letinstead ofvar - As
letis block scoped and would get the job done
function a() {
for (var i = 0 ; i < 3 ; i++) {
setTimeout(function log() {
console.log(i); // What is logged?
}, 1000);
}
}
a(); // ans: 3, 3, 3
Followup 2: how will you print without using let // 0, 1, 2
- Hint: use closures
function a() {
for (var i = 0 ; i < 3 ; i++) {
function inner(i) {
setTimeout(function log() {
console.log(i); // What is logged?
}, 1000);
}
inner(i);
}
}
a(); // ans: 3, 3, 3
Q5. How would you use a closure to create a private counter?
?
function counter() {
var _counter = 0;
function add(increment) {
_counter += increment;
}
function retrive() {
return "Counter = " + _counter;
}
return {
add,
retrive,
};
}
const c = counter();
c.add(5);
c.add(10);
console.log(c.retrive);
Q6. What is a Module Pattern JavaScript?
?
var Module = (function() {
function privateMethod() {
// do something
console.log("Private Method");
}
return {
publicMethod; function() {
// can call privateMethod();
console.log("Public Method");
},
};
})();
Module.publicMethod(); // Public Method
Module.privateMethod(); // Not a function
Q7. Make this run only once
let view;
function likeTheVideo() {
view = "Chaitanya";
console.log("Subscrible to", view);
}
likeTheVideo();
likeTheVideo();
likeTheVideo();
likeTheVideo();
?
Answer
let view;
function likeTheVideo() {
let called = 0;
return function () {
if (called > 0) {
console.log("Already Subscribed to Chaitanya");
} else {
view = "Chaitanya";
console.log("Subscrible to", view);
called++;
}
};
}
let isSubscribed = likeTheVideo();
isSubscribed();
isSubscribed();
isSubscribed();
isSubscribed();
Q8. Once Polyfill, to run a function once provided by lodash
?
function once(func, context) {
let ran;
return function () {
if (func) {
ran = func.apply(context || this, arguments); // Read about apply function
func = null;
}
reutrn ran;
};
}
const hello = once((a, b) => console.log("Hello", a, b));
hello(1, 2);
hello(1, 2);
hello(1, 2);
hello(1, 2);
Q9. Memoize Polyfill: Implement a Caching/Memoize Function
const clumsysquare = (num1, num2) {
for (let i = 1; i <= 10000000 ; i++) { }
return num1 * num2;
}
console.time("First Call");
console.log(clumsysquare(9467, 7649));
console.timeEnd("First Call");
console.time("Second Call");
console.log(clumsysquare(9467, 7649));
console.timeEnd("Second Call");
?
Answer
function myMemoize(fn, context) {
const res = {};
return function (...args) {
var argsCache = JSON.stringify(args);
if (!res[argsCache]) {
res[argsCache] = fn.call(context || this, ...args)
}
return res[argsCache];
};
}
const clumsyProduct = (num1, num2) {
for (let i = 1; i <= 10000000 ; i++) { }
return num1 * num2;
};
const memoizedClumsyProduct = myMemoize(clumsyProduct);
console.time("First Call");
console.log(memoizedClumsyProduct(9467, 7649));
console.timeEnd("First Call");
console.time("Second Call");
console.log(memoizedClumsyProduct(9467, 7649));
console.timeEnd("Second Call");
Q10. Difference between Closure & Scope
?
- Scope defines where variables are accessible in your code. There are three types:
global,local, andblockscope. - Closure is when a function retains access to variables from its outer scope even after the outer func has returned.
- This happens when you define a function inside another and use the outer function's variables in inner function
- In short, scope is about variable visibility, while closure is about a function "remembering" the environment it was created in.