This blog is primarily focus on Java fundamentals and the libraries built on top of Java programming language. Most of the post are example oriented, hope you have fun in reading my blog....:)
Showing posts with label JavaScript interview Questions. Show all posts
Showing posts with label JavaScript interview Questions. Show all posts
Saturday, 22 December 2018
JavaScript: Immediately invoked function expressions
An
Immediately invoked function expression (IIFE) is a function, that is invoked
as soon as it is defined.
Syntax
(function
() {
statements
})();
app.js
(function () { console.log('I will execute immediately') })()
Run
app.js, you will see below messages in console.
I
will execute immediately
You
can writhe the same snippet using named functions like below.
(function
sayHello(){
console.log('Hello World')
}())
You
can even pass arguments to IIFE.
app.js
(function (name, age){ console.log(`Hello ${name}, you are ${age} years old`) }('krishna', 10))
Run
app.js, you can see below messages in console.
Hello
krishna, you are 10 years old
You
can assign the return value of IIFE to a variable.
app.js
var message = (function (name, age){ return `Hello ${name}, you are ${age} years old` }('krishna', 10)) console.log(message)
Output
Hello
krishna, you are 10 years old
Explain about Generators in JavaScript
Generators
are used to define an iterative algorithm by writing a single function whose
execution is not continuous.
How to define a
generator?
'function*'
declaration used to define a generator function.
Example
function*
nextEvenNumber() {
yield 2;
yield 4;
yield 6;
yield 8;
}
HelloWorld.js
function* nextEvenNumber() { yield 2; yield 4; yield 6; yield 8; } var evenNumbers = nextEvenNumber(); console.log(evenNumbers.next()); // Get first yied, 2 console.log(evenNumbers.next()); // Get second yied, 4 console.log(evenNumbers.next()); // Get third yied, 6 console.log(evenNumbers.next()); // Get fourth yied, 8 console.log(evenNumbers.next()); // Get fifth yied, which is not there, undefined console.log(evenNumbers.next()); // Get sixth yied, which is not there, undefined
Output
Object
{ value: 2, done: false }
Object
{ value: 4, done: false }
Object
{ value: 6, done: false }
Object
{ value: 8, done: false }
Object
{ value: undefined, done: true }
Object
{ value: undefined, done: true }
evenNumbers.next()
Returns
a value yielded by the yield expression.
As
you see the output, 'evenNumbers.next()' method returns an object that contains
a value and a flag 'done'. Flag 'done' set to false, if next yield expression
is available, else false.
Let’s
enhance the above function to return infinite even numbers.
HelloWorld.js
function* nextEvenNumber() { var i = 0; while(true){ yield i; i += 2; } } var evenNumbers = nextEvenNumber(); /* Print first 10 even numbers */ for(var i=0; i < 10; i++){ console.log(evenNumbers.next().value); }
Output
0
2
4
6
8
10
12
14
16
18
Can a generator
function take arguments?
Yes,
a generator function takes arguments.
function*
name(param1, param2....paramN) {
statements
}
HelloWorld.js
function* nextEvenNumber(maxNumber) { var i = 0; while(i <= maxNumber){ yield i; i += 2; } } var evenNumbers = nextEvenNumber(10); var obj = evenNumbers.next(); while(!obj.done){ console.log(obj.value); obj = evenNumbers.next(); }
Output
0
2
4
6
8
10
JavaScript: Convert an element to array
Write
a program, that takes an element and return an array.
a. Element can be of any
type like number, boolean, string, object etc.,
b. If the element is
null (or) undefined, you should return an empty array.
c. If element is an
array itself, you should return ele only.
HelloWorld.js
function get_array(ele){ if(ele === null || ele === undefined){ return []; } if(Array.isArray(ele)) return ele; return [ele]; } console.log(get_array(null)); console.log(get_array(undefined)); console.log(get_array([])); console.log(get_array([123, 456])); console.log(get_array(123)); console.log(get_array("Krishna"));
Output
Array
[]
Array
[]
Array
[]
Array
[ 123, 456 ]
Array
[ 123 ]
Array
[ "Krishna" ]
What is __proto__ in JavaScript?
__proto__
is a property, it points to the object which was used as prototype when the
object was instantiated.
Let
me explain with an example.
HelloWorld.js
class A{ } class B extends A{ } class C extends B{ } var obj = new C(); var proto = obj.__proto__; while(proto != null){ console.log(proto.constructor); proto = proto.__proto__; }
As
you see above example, Class C is inheriting the properties from Class B, Class
B inherit from class A.
For
the object ‘obj’, class C is used as prototype,
for
the class C, class B is used as prototype,
for
the class B, class A is used as prototype.
For
the class A, Object class (it is the super class for all the classes) is used
as prototype.
When
you ran HelloWorld.js, you can see below messages in console.
What is prototype property in JavaScript?
‘prototype’
property is an object, that is associated with every object in JavaScript by
default.
HelloWorld.js
For
example,
HelloWorld.js
var obj = new Object(); console.log(obj);
When
you ran above script, you can see below messages in console.
If
you attach properties to a prototype property of a class, constructor function,
then those properties are visible to all the instance of the class.
HelloWorld.js
Object.prototype.version = "1.23"; Object.prototype.author = "krishna"; var obj1 = new Object(); var obj2 = new Object(); console.log("Version " + obj1.version); console.log("Author : " + obj1.author); console.log("Version " + obj2.version); console.log("Author : " + obj2.author);
Output
Version
1.23
Author
: krishna
Version
1.23
Author
: Krishna
Why should we attach
properties to prototype object?
Let
me try to explain with an example. Suppose, you are developing an application
to the organization ‘ABC Corp’. You modeled the Employee class like below.
function Employee(firstName, lastName, organization){ this.firstName = firstName; this.lastName = lastName; this.organization = organization; } var emp1 = new Employee('Krishna', 'Gurram', "ABC Corp"); var emp2 = new Employee('Siva', 'Ponname', "ABC Corp"); var emp3 = new Employee('Ram', 'Majety', "ABC Corp"); console.log(emp1); console.log(emp2); console.log(emp3);
Output
Object
{ firstName: "Krishna", lastName: "Gurram", organization:
"ABC Corp" }
Object
{ firstName: "Siva", lastName: "Ponname", organization:
"ABC Corp" }
Object
{ firstName: "Ram", lastName: "Majety", organization:
"ABC Corp" }
As
you see above snippet, you can observe that the organization has the value ‘ABC
Corp’ for all the employees. Then why should we duplicate this value. We can
attach the organization to the prototype property of the class Employee, so it
will be visible to all the employees.
HelloWorld.js
function Employee(firstName, lastName){ this.firstName = firstName; this.lastName = lastName; } Employee.prototype.organization = "ABC Corp"; var emp1 = new Employee('Krishna', 'Gurram'); var emp2 = new Employee('Siva', 'Ponname'); var emp3 = new Employee('Ram', 'Majety'); function printEmployeeInfo(emp){ console.log("firstName : " + emp.firstName); console.log("lastName : " + emp.lastName); console.log("organization : " + emp.organization); } printEmployeeInfo(emp1); printEmployeeInfo(emp2); printEmployeeInfo(emp3);
Output
firstName
: Krishna
lastName
: Gurram
organization
: ABC Corp
firstName
: Siva
lastName
: Ponname
organization
: ABC Corp
firstName
: Ram
lastName
: Majety
organization
: ABC Corp
What
if one of the employee is working as a consultant from different organization.
You can solve that by adding instance property to the employee object directly.
var
emp1 = new Employee('Krishna',
'Gurram');
emp1.organization
= "XYZ Corporation";
HelloWorld.js
function Employee(firstName, lastName){ this.firstName = firstName; this.lastName = lastName; } Employee.prototype.organization = "ABC Corp"; var emp1 = new Employee('Krishna', 'Gurram'); emp1.organization = "XYZ Corporation"; var emp2 = new Employee('Siva', 'Ponname'); function printEmployeeInfo(emp){ console.log("firstName : " + emp.firstName); console.log("lastName : " + emp.lastName); console.log("organization : " + emp.organization); } printEmployeeInfo(emp1); printEmployeeInfo(emp2);
Output
firstName
: Krishna
lastName
: Gurram
organization
: XYZ Corporation
firstName
: Siva
lastName
: Ponname
organization
: ABC Corp
instance property vs prototype
property
Instance
property is specific to given object, whereas prototype property is attached to
the class (or) function prototype property, and is available for all the
objects.
HelloWorld.js
function Employee(firstName, lastName){ this.firstName = firstName; this.lastName = lastName; } Employee.prototype.organization = "ABC Corp"; var emp1 = new Employee('Krishna', 'Gurram'); emp1.organization = "XYZ Corporation"; console.log(emp1);
Output
How to access
prototype property?
If
instance property and prototype property names are same, then you can use
__proto__ property to access the prototype property of an object.
Example
emp1.__proto__.organization
HelloWorld.js
function Employee(firstName, lastName){ this.firstName = firstName; this.lastName = lastName; } Employee.prototype.organization = "ABC Corp"; var emp1 = new Employee('Krishna', 'Gurram'); emp1.organization = "XYZ Corporation"; console.log(emp1.organization); console.log(emp1.__proto__.organization);
Output
XYZ
Corporation
ABC
Corp
node.js: module.exports vs exports
In
this post, I am going to explain the difference between module.exports and
exports.
Whenever
you load a module using require() function, it returns module.exports object of
that module.
For
example,
util.js
module.exports = { productName : "chat server", version : "1.2.3" }
index.js
util = require("./util.js") console.log(`name : ${util.productName}`) console.log(`version : ${util.version}`)
Execute
the command ‘node index.js’, you can see below messages in console.
name
: chat server
version
: 1.2.3
What is exports?
exports
is a reference to module.exports. If you attach any property to exports those
are attached to module.exports also.
util.js
module.exports.productName = "chat server" // Adding properties using exports exports.version = "1.2.3" exports.vendor = "ABC Corporation"
index.js
util = require("./util.js") console.log(`name : ${util.productName}`) console.log(`version : ${util.version}`) console.log(`vendor : ${util.vendor}`)
Run
index.js, you can see below messages in console.
name
: chat server
version
: 1.2.3
vendor
: ABC Corporation
if
module.exports pointing to some other object directly, then the properties
exposed by export are ignored.
util.js
module.exports = { productName : "chat server" } // Adding properties using exports, these will be ignored exports.version = "1.2.3" exports.vendor = "ABC Corporation"
index.js
util = require("./util.js") console.log(`name : ${util.productName}`) console.log(`version : ${util.version}`) console.log(`vendor : ${util.vendor}`)
Output
name
: chat server
version
: undefined
vendor
: undefined
As
you see the output, vendor and version details are undefined. It is because,
module.exports is assigned to another object directly. So whatever you exposed
via export will be ignored.
JavaScript: Explain about module.exports
Whenever
you load a module using require() function, it returns module.exports object of
that module.
Let
me explain with an example.
models.js
function Employee(firstName, lastName, addr){ this.firstName = firstName; this.lastName = lastName; this.addr = addr; this.printInfo = function(){ console.log("firstName : " + this.firstName); console.log("lastName : " + this.lastName); this.addr.printInfo(); } } function Address(city, country){ this.city = city; this.country = country; this.printInfo = function(){ console.log("city : " + this.city); console.log("country : " + this.country); } } module.exports.Employee = Employee; module.exports.Address = Address;
As
you see models.js, I exported Employee and Address functions. So whoever
loading the module models.js using require function, those can acceess Employee
and Address constructor functions.
module.exports.Employee
= Employee;
module.exports.Address
= Address;
app.js
var models = require("./models.js"); var Employee = models.Employee; var Address = models.Address; var addr = new Address("Bangalore", "India"); var emp = new Employee("Krishna", "Gurram", addr); emp.printInfo();
$node
app.js
firstName
: Krishna
lastName
: Gurram
city
: Bangalore
country
: India
You
can even export the functions, types or anything in the module using object
literal notation like below.
module.exports
= {
Employee : Employee,
Address : Address
}
Example 2
Emp.js
function Employee(firstName, lastName){ this.firstName = firstName; this.lastName = lastName; this.printInfo = function(){ console.log("firstName : " + this.firstName); console.log("lastName : " + this.lastName); } } module.exports = Employee;
App.js
const Employee = require("./Emp.js"); var emp = new Employee('Krishna', 'Gurram'); emp.printInfo();
Output
firstName
: Krishna
lastName
: Gurram
While
loading the module using require function, you no need to specify .js file
extension.
const
Employee = require("./Emp");
What are Arrow function expressions in JavaScript?
Arrow
functions are compact way of creating a function.
HelloWorld.js
HelloWorld.js
Let
me explain with an example.
HelloWorld.js
var printArrayElements = function(arr){ for(var data of arr){ console.log(data); } } var primeNumbers = [2, 3, 5, 7, 11]; printArrayElements(primeNumbers);
As
you see above snippet, printArrayElements function takes an iterable as an
argument and print all the elements of the iterable.
We
can rewrite the printArrayElements function using arrow function expression
like below.
var
printArrayElements = (arr) => {
for(var data of arr){
console.log(data);
}
}
var printArrayElements = (arr) => { for(var data of arr){ console.log(data); } } var primeNumbers = [2, 3, 5, 7, 11]; printArrayElements(primeNumbers);
Syntax to define
arrow functions
(param1,
param2, …, paramN) => { statements }
(param1,
param2, …, paramN) => expression
(singleParam)
=> { statements }
singleParam
=> { statements }
()
=> { statements }
One
advantage of arrow functions is that, these arrow function expressions does not
have its own this, arguments, super, or new.target.
Let
me explain with an example.
var person = { name : "Krishna", hobbies : ["Cricket", "Puzzles", "Blogging"], printHobbies : function(){ this.hobbies.forEach(function(hobby){ //this.name is not visible here. console.log(this.name + " has hobby " + hobby); }); } }; person.printHobbies();
Output
has hobby Cricket
has hobby Puzzles
has hobby Blogging
As
you see the output, this.name is not printing the name ‘krishna’, it is
because, this.name is not visible inside the function defined in forEach.
How to resolve above
issue?
a. By keeping the
reference of this (outer object)
b. By using bind()
method.
By keeping the reference
of this (outer object)
HelloWorld.js
var person = { name : "Krishna", hobbies : ["Cricket", "Puzzles", "Blogging"], printHobbies : function(){ var _this = this; this.hobbies.forEach(function(hobby){ //this.name is not visible here. console.log(_this.name + " has hobby " + hobby); }); } }; person.printHobbies();
Output
Krishna
has hobby Cricket
Krishna
has hobby Puzzles
Krishna
has hobby Blogging
By using bind()
method
‘bind()’
method creates a new function that, when called, has its this keyword set to
the provided value
HelloWorld.js
var person = { name : "Krishna", hobbies : ["Cricket", "Puzzles", "Blogging"], printHobbies : function(){ this.hobbies.forEach(function(hobby){ console.log(this.name + " has hobby " + hobby); }.bind(this)); } }; person.printHobbies();
Output
Krishna
has hobby Cricket
Krishna
has hobby Puzzles
Krishna
has hobby Blogging
From
EcmaScript 6 onwards, we can use arrow functions to solve above kind of
problems. Since arrow function expressions does not have its own this, we no
need to worry about this problem.
HelloWorld.js
var person = { name : "Krishna", hobbies : ["Cricket", "Puzzles", "Blogging"], printHobbies : function(){ this.hobbies.forEach(hobby => { console.log(this.name + " has hobby " + hobby); }); } }; person.printHobbies();
Output
Krishna
has hobby Cricket
Krishna
has hobby Puzzles
Krishna
has hobby Blogging
Subscribe to:
Posts (Atom)


