This is a collection of JavaScript tips and tricks. you can refer to it and apply it to make your code more concise. But don't overdo it, it can make your code difficult to read and maintain. Hope everyone contributes, thanks.
1. Generate an Array
-
Create an empty array of length
n
var arr = new Array(3); // result: arr = [undefined, undefined, undefined]
-
Create an empty array of length
n
& fill valuex
var arr = [...Array(3).fill(1)]; var arr2 = [...Array(5).fill(1, 0, 3)]; /* result: arr = [1, 1, 1] arr2 = [1, 1, 1, undefined, undefined] */
-
Create an array containing
0...n
var arr = [...Array.keys(5)]; // result: arr = [0, 1, 2, 3, 4]
-
Create an array containing
1...n
var arr = []; for (let i = 0; arr.push(++i) < 4; ); var arr2 = Array.from({ length: 4 }, (_, i) => i + 1); var arr3 = Array.from({ length: 4 }, (_, i) => i * 2); var arr4 = Array.from({ length: 4 }, () => Math.random()); /* result: arr = [1, 2, 3, 4] arr2 = [1, 2, 3, 4] arr3 = [0, 2, 4, 6] arr4 = [0.211, 0.5123, 0.612, 0.8921] */
2. Extract Unique Values of Array
var arr = [1, 2, 2, 3, 5, 5, 4];
var newArr = [...new Set(arr)];
// result: newArr = [1, 2, 3, 5, 4]
3. Shuffle Elements from Array
var arr = [1, 2, 3, 4, 5];
var newArr = arr.sort(() => Math.random() - 0.5);
// result: newArr = [3, 1, 2, 4, 5]
4. Flatten a Multidimensional Array
var arr = [1, [2, 3], [4, 5, 6], 7];
var newArr = [].concat(...arr);
// result: [1, 2, 3, 4, 5, 6, 7]
5. Resize an Array
The length array isn't a read only property.
var arr = [1, 2, 3, 4, 5];
arr.length = 2;
var arr2 = [1, 2, 3, 4, 5];
arr2.length = 0;
var arr3 = [1, 2, 3, 4, 5];
arr3.length = 7;
/*
result: arr = [1, 2]
arr2 = []
arr3 = [1, 2, 3, 4, 5, undefined, undefined]
*/
6. Random an Item in Array
var arr = [2, 4, 5];
var item = arr[Math.floor(Math.random() * arr.length)];
7. Remove an Item from Array
var arr = [1, 2, 3];
// Not Recommended
delete arr[1]; // arr = [1, undefined, 3], length = 3
// Recommended
arr.splice(1, 1); // arr = [1, 3], length = 2
1. Dynamic Property Name
const dynamic = 'age',
dynamicValue = 18;
var obj = {
name: 'Dyno',
[dynamic]: dynamicValue,
};
// result: obj = { name: 'Dyno', age: 18 }
2. Clone an Object
-
Shallow copy
(Not Recommended)
Use the
=
operator to copy object 1 into object 2. These 2 objects point to the same memory area(reference)
. Therefore, if we change object 1, object 2 will also change.var obj1 = { a: 1, b: 2 }; var obj2 = obj1; // obj2 = { a: 1, b: 2 } obj1.a = 3; // change value of a property console.log(obj1); // { a: 3, b: 2 } console.log(obj2); // { a: 3, b: 2 } => property a of obj2 changed πβ console.log(obj3); // { a: 3, b: 2 } => property a of obj2 changed πβ
-
Deep copy
Way 1: Use Spread operator
{...}
orObject.assign()
to fix "Shallow copy". Issue:Nested objects
still have shallow copy problem.var obj1 = { a: 1, b: 2, c: { nested: 3 } }; var obj2 = { ...obj1 }; // obj2 = { a: 1, b: 2, c: { nested: 3 } } var obj3 = Object.assign({}, obj1); // obj3 = { a: 1, b: 2, c: { nested: 3 } } obj1.b = 3; obj1.c.nested = 4; console.log(obj1); // { a: 1, b: 3, c: { nested: 4 } } console.log(obj2); // { a: 1, b: 2, c: { nested: 4 } } π console.log(obj3); // { a: 1, b: 2, c: { nested: 4 } } π
Way 2
(Recommended)
: UseJSON.stringify()
&JSON.parse()
to solve the above problems.var obj1 = { a: 1, b: 2, c: { nested: 3 } }; var obj2 = JSON.parse(JSON.stringify(obj1)); // obj2 = { a: 1, b: 2, c: { nested: 3 } } obj1.b = 3; obj1.c.nested = 4; console.log(obj1); // { a: 1, b: 3, c: { nested: 4 } } console.log(obj2); // { a: 1, b: 2, c: { nested: 3 } } ππ
1. With Array
var [a, b] = [1, 2];
// same: var a = 1, b = 2;
var [a, b, c] = [1, 2, 3, 4, 5];
// same: var a = 1, b = 2, c = 3;
var [a, , c] = [1, 2, 3, 4, 5];
// same: var a = 1, c = 3
// ignore values
var [a, b, ...rest] = [1, 2, 3, 4, 5];
// same: var a = 1, b = 2, rest = [4, 5]
// use "rest params ES6"
var [a, b, c] = [1, 2];
// same: var a = 1, b = 2, c = undefined;
var [a, b = 0, c = 0] = [1, 2];
// same: var a = 1, b = 2, c = 0;
// declare and set default value
var [a, b, [c, d], e] = [1, 2, [3, 4], 5];
// same: var a = 1, b = 2, c = 3, d = 4, e = 5
// nested array destructuring
2. With Object
var person = { name: 'Dyno', age: 18 };
var { name, age } = person;
// same: var name = person.name, age = person.age;
var { name = 'Anonymous', age = 1, address = 'HCM city' } = person;
// same: var name = person.name, age = person.age, address: 'HCM city'
// declare and set default value
var { name: personName, age: personAge } = person;
// same: var personName = person.name, personAge = person.age
// decleare and change variable name
console.log({ name, age });
// same: console.log({ name: name, age: age })
var person = { name: 'Dyno', age: 18, infor: { address: 'HCM', phone: '123' } };
var {
name,
age,
infor: { address, phone },
} = person;
// same: name = person.name, age = person.agem, address = person.infor.address, phone = person.infor.phone
// nested object destructuring
1. Optional chaining (?.)
"The optional chaining operator
?.
enables you to read the value of a property located deep within a chain of connected objects without having to check that each reference in the chain is valid." MDN
const person = {
name: 'Dyno',
age: 18,
sayHello: function () {
console.log('Hello');
},
};
// β Wrong way
console.log(person.infor.address); // β Uncaught TypeError: Cannot read property 'address' of undefined
// β
Right way (check condition)
if (person.infor) console.log(person.infor.address); // Not log
// β
Right way (use ?.)
console.log(person.infor?.address); // undefined
// Optional chaining with function calls
console.log(person.sayHello?.()); // Hello
console.log(person.callPhone?.()); // undefined
// A chain Optional chaining
console.log(person.infor?.address?.province?.name); // undefined
// syntax
obj.val?.prop;
obj.val?.[expr];
obj.arr?.[index];
obj.func?.(args);
2. Nullish coalescing operator (??)
"The nullish coalescing operator
??
is a logical operator that returns its right-hand side operand when its left-hand side operand isnull
orundefined
, and otherwise returns its left-hand side operand." MDN
var a = null ?? 'Default'; // a = 'Default'
var a = false ?? 'Default'; // a = false
3. Logical OR (||)
var a = 1,
b = 2;
if (a > 2 || b > 1) console.log('Dyno');
// result: Dyno
The OR operator
||
is a logical operator that returns its right-hand side operand when its left-hand side operand isfalsy
, and otherwise returns its left-hand side operand.
var a = null || 'Default'; // a = 'Default'
var a = false || 'Default'; // a = 'Default'
4. Logical AND (&&)
let a = true,
b = true,
c = false;
if (a && b) console.log('Hello'); // Hello (a, b = true)
if (a && c) console.log('Dyno'); // not log (c = false)
// other usage
function sayHi() {
console.log('Hi');
}
a && sayHi(); // Hi
c && sayHi(); // false
5. Double tilde operator (~~)
let num = 2.6;
console.log(~~num); // 2 = Math.floor(2)
6. Logical Assignment Operator ES12 (||=, ??=)
a ||= b; // same a = a || b;
a ??= b; // same a = a ?? b;
7. Numeric separator ES12 (_)
const n = 1_000_000_000; // same: n = 1000000000;
1. Use === instead of ==
The operator
== (!=)
will automatically cast if 2 variables are not of the same type, then compare. The=== (!==)
operator compares the value and the type =>===
faster than==
.
1 == '1' // true
1 === '1' // false
0 == false // true
0 === false // false
'' == false // false
'' === false // true
[] == 0 // false
[] === 0 // true
2. The difference between isNaN() and Number.isNaN()
The
isNaN()
method (is Not a Number ?) use to check if a variable is a Number. TheNumber.isNaN()
(is NaN ?) method use to check if a variable is NaN
isNaN('string');
// true, 'string' is not Number
isNaN([]);
// true, [] is not Number
isNaN(0 / 0);
// true, 0/0 is not Number
isNaN(1);
// false, 1 is Number
Number.isNaN('string');
// false, 'string' is not NaN
Number.isNaN([]);
// false, [] is not NaN
Number.isNaN(0 / 0);
// true, 0/0 is NaN
Number.isNaN(NaN);
// true
1. Swapping use Destructuring
let a = 1,
b = 2;
[a, b] = [b, a];
// result: a = 2, b = 1;
2. Create function that returns only 1 object
const fn = () => ({ obj: 1 });
/*
same: const fn = () => {
return { obj: 1 }
}
*/
3. Immediately Invoked Function Expression (IIFE)
The function will execute automatically when you create it.
// Way 1:
var res = ()(function(){
// do something...
console.log("Hello");
return true;
})();
// result: Hello, res = true;
// Way 2:
var res = (() => {
console.log('Hello');
return true;
})();
// result: Hello, res = true;
4. typeof vs instanceof
typeof
: return a string that represents the primitive type of a variable.
instanceof
: check in all the prototypes chain the constructor it returns true if itβs found and false if not.
var arr = [1, 2, 3];
console.log(typeof arr); // "object"
console.log(arr instanceof Array); // true
typeof 1; // "number"
typeof NaN; // "number"
typeof 'str'; // "string"
typeof true; // "boolean"
typeof {}; // "object"
typeof []; // "object"
typeof null; // "object"
typeof undefined; // "undefined"
typeof function name() {}; // "function"
5. Falsy
A
Falsy value
is a value that is considered false when encountered in a Boolean context . MDN
Complete list of JavaScript falsy values
false, 0, -0, 0n, "", '', ``, NaN, null, undefined, document.all
Falsy value bypass the if block. Ex:
if (null) {
} else {
console.log('Falsy');
}
const a = undefined || 'Falsy';
// result: Falsy, a = "Falsy"
Filter out Falsy values
const arr = [1, 'Dyno', false, 0, true, NaN, 2000];
var filteredArr = arr.filter(Boolean);
// result: filteredArr = [1, "Dyno", true, 2000]
6. Template string `${}`
const name = 'Dyno';
const hello1 = 'Hello ' + name + ', how are you?';
const hello2 = `Hello ${name}, how are you?`; // template string
7. Rounding number to n decimal place
var num = 25.0420001;
console.log(typeof num); // "number"
num = num.toFixed(2); // num = "25.04"
console.log(typeof num); // β "string"