08 April 2023

Javascript Basic

    __          _ ____        _          ____  __      _           __ 
   / /_  __  __(_) / /_      (_)___     / __ \/ /_    (_)__  _____/ /_
  / __ \/ / / / / / __/_____/ / __ \   / / / / __ \  / / _ \/ ___/ __/
 / /_/ / /_/ / / / /_/_____/ / / / /  / /_/ / /_/ / / /  __/ /__/ /_  
/_.___/\__,_/_/_/\__/     /_/_/ /_/   \____/_.___/_/ /\___/\___/\__/  
                                                /___/
                                                       __    ___   ___    __    _    
                                                      / /\  | |_) | |_)  / /\  \ \_/ 
                                                     /_/--\ |_| \ |_| \ /_/--\  |_|

Object

Boolean

Check is Object
obj.constructor === Object // true
function isObject(value) {
  return Object.prototype.toString.call(value) === "[object Object]";
}

Other

assign
const target = { a: 1, b: 2 };
const source = { b: 3, c: 4 };

const newTarget = Object.assign(target, source); // { a: 1, b: 3, c: 4 }

target === newTarget // true
fromEntries
const entries =[
  ['foo', 'bar'], // [key, value]
  ['baz', 42]
];

Object.fromEntries(entries); // { foo: "bar", baz: 42 }
getOwnPropertyNames
const object1 = {
  a: 1,
  b: 2,
  c: 3
};

Object.getOwnPropertyNames(object1) // ["a", "b", "c"]
hasOwn
const object1 = {
  prop: 'exists'
};

Object.hasOwn(object1, 'prop') // true
hasOwnProperty
const object1 = {
  prop: 'exists'
};

object1.hasOwnProperty('prop') // true

// Ngoài ra còn có in để kiểm tra sự tồn tại property
const object1 = {
  prop: 'exists'
};

"prop" in object1 // true
is - compare object
const obj = {a: 1};

Object.is(obj, obj); // true
freeze - Đóng băng
const obj = { prop: 42, child: { id: 1 } };

Object.freeze(obj);

// Parent
// No: Create, Update, Delete
obj.prop = 33;
obj.prop2 = 33;
delete obj.prop;

// Child
// Yes: Create, Update, Delete
obj.child.id = 2;
obj.child.id1 = 2;
obj.child.id2 = 2;
delete obj.child.id2;

console.log(Object.isFrozen(obj)) // true
console.log(obj) // { prop: 42, child: { id: 2, id1: 2 } }
seal - Niêm phong
const obj = { prop: 42, child: { id: 1 } };

Object.seal(obj);

// Parent
// Yes: Update
obj.prop = 33;
// No: Create, delete
obj.prop1 = 33;
delete obj.prop

// Child
// Yes: Create, Update, Delete 
obj.child.id = 2;
obj.child.id1 = 2;
obj.child.id2 = 2;
delete obj.child.id2;

console.log(Object.isSealed(obj)) // true
console.log(obj) // { prop: 33, child: { id: 2, id1: 2 } }
isExtensible - preventExtensions - Mở rộng
const obj = { prop: 42, child: { id: 1 } };

console.log(Object.isExtensible(obj)); // true

console.log(Object.preventExtensions(obj)); // { prop: 42, child: { id: 1 } }

console.log(Object.isExtensible(obj));  // false


// Parent
// Yes: Delete
delete obj.prop;
// No: Create, Update
obj.prop = 2
obj.prop2 = 2

// Child
// Yes: Create, Update, Delete 
obj.child.id = 2;
obj.child.id1 = 2;
obj.child.id2 = 2;
delete obj.child.id2;

console.log(obj) // { child: { id: 2, id1: 2 } }
keys
const object1 = {
  a: 'somestring',
  b: 42,
  c: false
};

console.log(Object.keys(object1)); // ["a", "b", "c"]
values
const object1 = {
  a: 'somestring',
  b: 42,
  c: false
};

console.log(Object.values(object1)); // ["somestring", 42, false]
Remove property
const { name, ...rest } = { name: 'Foo', age: 20 };

console.log(name); // 'Foo'
console.log(rest); // { age: '20' }
Unpack property object
const person = {
    name: 'John Doe',
};

const { name } = person; // name = 'John Doe'

// Or unpack with other name
const { name: fullName } = person; // fullName: 'John Doe'

https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object

Array

New Array

new array by number
[...Array(10).keys()]
// [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]

Array.from(Array(10).keys())
// [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]

Array.from({length: 10}, (_, i) => i + 1)
// [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
clone an array
const originalArray = [1, 2, 3];

originalArray.slice() or originalArray.slice(0)

[...originalArray]

Array.from(originalArray)

[].concat(originalArray);

originalArray.map(x => x);

Array.from(originalArray, x => x);

Array.of(...originalArray);

JSON.parse(JSON.stringify(originalArray));

Object.assign([], originalArray);
from
Array.from('123'); // ['1', '2', '3']

Array.from([1, 2, 3], x => x + x); // [2, 4, 6]
  
Array.from({length: 10}, (_, i) => i + 1); // [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
of
Array.of(1,2,3,true); // [1, 2, 3, true]

Array.of(); // []

Boolean

Check is Array
Array.isArray([1, 2, 3]);  // true
'length' in arr // true
arr.constructor === Array // true
function isArray(arr){
  return Object.prototype.toString.call(arr) === '[object Array]'
}
instanceof
arr instanceof Array // object
some - every
// some: Một trong số đúng điều kiện thì trả về true
// every: Tất cả phải đúng với điều kiện thì trả về true

console.log([true, false].some(x => x)) // true
console.log([true, false].every(x => x)) // false
includes
console.log([1,2].includes(1)); // true
console.log("demo abc".includes('abc')); // true

Find

find - filter
[1,2,3].find(x => x === 2) // 2

[1,2,3].filter(x => x < 2) // [1]
indexOf - lastIndexOf
[1,2,3].indexOf(2) // 1

[1,2,3].lastIndexOf(1) // 0

Modified - return new array

concat
[1, 2, 3].concat([4]) // [1, 2, 3, 4]
    
Array.prototype.concat([1, 2, 3], [4]); // [1, 2, 3, 4]

// Gợi ý thêm string cũng có thể concat
"text1".concat(" ", "text2"); // "text1 text2"
join
[1, 2, 3].join('-') // '1-2-3'
slice
[1, 2, 3].slice(1) // [2, 3]
  
[1, 2, 3].slice(-1) // [3]
  
[1, 2, 3].slice(0,2) // [1, 2]
map
[1,2,3].map(x => x * 2) // [2, 4, 6]
reduce
let index = 0; // Chỉ số 
[1,2,3].reduce((accumulator,current) => accumulator * current, index) // 6

https://gist.github.com/id1945/c5a89e5b87f26b1e0237d39df55bd44c

fill
[1,2,3].fill(0, 2, 4) // [1, 2, 0]

[1,2,3].fill(5, 1)  // [1, 5, 5]

[1,2,3].fill(6) // [6, 6, 6]
flat - flatMap
[0, 1, 2, [3, 4]].flat() // [0, 1, 2, 3, 4]

[0, 1, 2, [[[3, 4]]]].flat(2)  // [0, 1, 2, [3, 4]]

[1, 2, [3], [4, 5], 6, []].flatMap(num => num) // [1, 2, 3, 4, 5, 6]
toSorted
const arr = [
  { name: 'D2', position: 1, iteration: 0 },
  { name: 'D1', position: 0, iteration: 0 },
  { name: 'D3', position: 0, iteration: 1 },
  { name: 'D4', position: 1, iteration: 1 },
];

// Trả về một mảng mới với các phần tử được sắp xếp
const newArr = arr.toSorted((a, b) => {
  if (a.iteration > b.iteration) {
    return 1;
  } else if (a.iteration < b.iteration) {
    return -1;
  } else {
    // a.iteration === b.iteration
    // có thể kiểm tra theo điều kiện thứ 2
    // ví dụ: if(a.title > b.title) ...
    return a.position > b.position ? 1 : -1;
  }
});

newArr.forEach((v) => console.log(v))
  
// { name: "D1", position: 0, iteration: 0 }
// { name: "D2", position: 1, iteration: 0 }
// { name: "D3", position: 0, iteration: 1 }
// { name: "D4", position: 1, iteration: 1 }
toReversed
[1,2,3].toReversed() // [3, 2, 1]
toSpliced
let arr = [1,2,3]

// Add
arr.toSpliced(1, 0, 'two') // [1, "two", 2, 3]

// Update
arr.toSpliced(1, 1, 'Update') // [1, "Update", 3]

// Delete
arr.toSpliced(1, 1) // [1, 3]
with
[1,2,3].with(2, 6) // [1, 2, 6]

Modified - return reference array

sort
const arr = [
  { name: 'D2', position: 1, iteration: 0 },
  { name: 'D1', position: 0, iteration: 0 },
  { name: 'D3', position: 0, iteration: 1 },
  { name: 'D4', position: 1, iteration: 1 },
];

// Trả về tham chiếu đến cùng một mảng
arr.sort((a, b) => {
  if (a.iteration > b.iteration) {
    return 1;
  } else if (a.iteration < b.iteration) {
    return -1;
  } else {
    // a.position === b.position
    // có thể kiểm tra theo điều kiện thứ 2
    // ví dụ: if(a.title > b.title) ...
    return a.position > b.position ? 1 : -1;
  }
});

arr.forEach((v) => console.log(v))

// { name: "D1", position: 0, iteration: 0 }
// { name: "D2", position: 1, iteration: 0 }
// { name: "D3", position: 0, iteration: 1 }
// { name: "D4", position: 1, iteration: 1 }
reverse
const arr = [1,2,3]
arr.reverse()
// arr: [3, 2, 1]

Add & Delete - return reference array

unshift - shift
let arr = [1,2,3]

// Add
const a = arr.unshift(5)
// arr: [5,1,2,3]
// a: 4 (length)

// Delete
const a = arr.shift()  
// arr: [2,3], 
// a: 1 (value)
push - pop
let arr = [1,2,3]

// Add
const a = arr.push('test')
// arr: [1, 2, 3, 'test'] 
// a: 4 (length)


// Delete
const a = arr.pop(1)
// arr: [1, 2] 
// a: 3 (value)
splice
// splice(start, deleteCount, item1, item2, itemN)

let arr = [1,2,3]

// Add
const a = arr.splice(1, 0, 'two')
// arr: [1, 'two', 2, 3]
// a: []


// Update
const a = arr.splice(1, 1, 'Update')
// arr: [1, 'Update', 3]
// a: [2] (value)


// Delete
const a = arr.splice(1, 1)
// arr: [1, 3]
// a: [2] (value)

Advance

group by - fromEntries
const items = [
  {
    type: 'fruit',
    value: '🍎',
  },
  {
    type: 'fruit',
    value: '🍇',
  },
  {
    type: 'fruit',
    value: '🍊',
  },
  {
    type: 'vegetable',
    value: '🥦',
  },
  {
    type: 'vegetable',
    value: '🥕',
  },
  {
    type: 'vegetable',
    value: '🌶️',
  },
];

const uniq = new Set(items.map(({ type }) => type));
const data = Array.from(uniq).map((type) => [type, items.filter((item) => item.type === type)]);
const output = Object.fromEntries(data);

// uniq: Set(2) {'fruit', 'vegetable'}
// data: [['fruit', Array(3)], ['vegetable', Array(3)]]
// output: {fruit: Array(3), vegetable: Array(3)}
group by - reduce
const output = items.reduce(
  (acc, item) => ({
    ...acc,
    [item.type]: [...(acc[item.type] ?? []), item],
  }),
  {},
);

// output: {fruit: Array(3), vegetable: Array(3)}
const output = items.reduce((acc, item) => {
  if (acc[item.type]) {
    acc[item.type].push(item);
  } else {
    acc[item.type] = [item];
  }

  return acc;
}, {});

// output: {fruit: Array(3), vegetable: Array(3)}

Function

Call
  • Call mục đích thay object mới cho this hiện tại của function
function Product(name, price) {
  this.name = name;
  this.price = price;
}

// CALL
function Food(name, price) {
  Product.call(this, name, price);
  this.category = 'food';
}

const food = new Food('cheese', 5);
console.log(food.name); // "cheese"
console.log(food.price); // 5
console.log(food.category); // "food"
const obj = {
  prod1: 'prod1',
  prod2: 'prod2',
  display: function (param1, param2) {
    console.log(this.prod1, this.prod2, param1, param2);
  },
};

const objNew = {
  prod1: 'prod1_new',
  prod2: 'prod2_new',
};

// CALL
obj.display.call(objNew, 'param1', 'param2'); // "prod1_new" "prod2_new" "param1" "param2"
Bind
  • Bind mục đích thay object mới cho this hiện tại của function
  • Phải gán cho biến mới và gọi biến đó để chạy
const module = {
  x: 42,
  getX: function() {
    return this.x;
  }
};

const unboundGetX = module.getX;
console.log(unboundGetX()); // The function gets invoked at the global scope
// Expected output: undefined

const boundGetX = module.getX.bind(module);
console.log(boundGetX());
// Expected output: 42
const obj = {
  prod1: 'prod1',
  prod2: 'prod2',
  display: function (param1, param2) {
    console.log(this.prod1, this.prod2, param1, param2);
  },
};

const objNew = {
  prod1: 'prod1_new',
  prod2: 'prod2_new',
};

// BIND
const func = obj.display.bind(objNew, 'param1', 'param2');
func(); // => "prod1_new" "prod2_new" "param1" "param2"
Apply
  • Apply mục đích thay object mới cho this hiện tại của function
  • Param truyền phải là mảng
const obj = {
  prod1: 'prod1',
  prod2: 'prod2',
  display: function (param1, param2) {
    console.log(this.prod1, this.prod2, param1, param2);
  },
};

const objNew = {
  prod1: 'prod1_new',
  prod2: 'prod2_new',
};

// APPLY
obj.display.apply(objNew, ['param1', 'param2']); // "prod1_new" "prod2_new" "param1" "param2"

Global functions

eval
console.log(eval('2 + 2')); // 4
isFinite
console.log(isFinite(1000), isFinite(10/0)); // true, false
isNaN
console.log(isNaN('100QQ'), isNaN('1E+10')); // true, false
decodeURI
console.log(encodeURI('?search=putin&age=70&wife=Lyudmila Aleksandrovna Ocheretnaya')); // ?search=putin&age=70&wife=Lyudmila%20Aleksandrovna%20Ocheretnaya

console.log(decodeURI('?search=putin&age=70&wife=Lyudmila%20Aleksandrovna%20Ocheretnaya')); // ?search=putin&age=70&wife=Lyudmila Aleksandrovna Ocheretnaya
    
console.log(encodeURIComponent('?search=putin&age=70')); // "%3Fsearch%3Dputin%26age%3D70"

console.log(decodeURIComponent('"%3Fsearch%3Dputin%26age%3D70"')); // ?search=putin&age=70

Collections

Map
  • Map cấu trúc dạng key - value
  • Key trong map là unique
  • Key là string, number
const map1 = new Map();

map1.set('a', 1);
map1.set('b', 2);
map1.set('c', 3);

// CRUD

// Create
console.log(map1.set('d', 97).get('d')); // 97

// Read
console.log(map1.get('a')); // 1

// Update
console.log(map1.set('a', 100).get('a')); // 100

// Delete
console.log(map1.delete('b')); // true

// Size
console.log(map1.size); // 3

// Has
console.log(map1.has("a")); // true

// clear
// map1.clear(); 

// Loop
map1.forEach((value, key) => console.log(`${key} = ${value}`)); 
// "a = 100"
// "c = 3"
// "d = 97"

for (const [key, value] of map1) {
  console.log(`${key} = ${value}`);
}
// "a = 100"
// "c = 3"
// "d = 97"

for (const key of map1.keys()) {
  console.log(key);
}
// "a"
// "c"
// "d"

for (const value of map1.values()) {
  console.log(value);
}
// 100
// 2
// 97

for (const [key, value] of map1.entries()) {
  console.log(`${key} = ${value}`);
}
// "a = 100"
// "c = 3"
// "d = 97"
Set
  • Set cấu trúc dạng value
  • Value trong set là unique
  • Value là number, string, Object
const set1 = new Set();

// CD

// Create
set1.add('Demo1');
set1.add('Demo2');
set1.add({ a: 1, a: 1, b: 2 }); // Phần tử trong set là unique { a: 1, b: 2 }

// Delete
console.log(set1.delete('Demo1')); // true

// Has
console.log(set1.has('Demo2')); // true

// Size
console.log(set1.size); // 2

// clear
// set1.clear();

// Loop
for (const item of set1) {
  console.log(item);
}
// "Demo2"
// { a: 1, b: 2 }


for (const item of set1.keys()) {
  console.log(item);
}
// "Demo2"
// { a: 1, b: 2 }

for (const item of set1.values()) {
  console.log(item);
}
// "Demo2"
// { a: 1, b: 2 }

for (const [key, value] of set1.entries()) {
  console.log(key);
}
// "Demo2"
// { a: 1, b: 2 }

console.log(Array.from(set1));
// ["Demo2", { a: 1, b: 2 }]

// Convert to array
let char = new Set(['a', 'b', 'c']);
console.log([...char]) // ['a', 'b', 'c']
WeakMap
  • WeakMap chỉ có thể chứa key dạng object.
  • WeakMaps cũng có các method giống như Map là get(), set(), delete() và has()
  • WeakMaps không thể lặp các phần tử
const weakMap = new WeakMap();
WeakSets
  • WeakSet chỉ có thể chứa các đối tượng
  • WeakSets có phương pháp add(), delete()và has()
  • WeakSets không thể lặp
const weakSets = new WeakSets();
$$$$$$$$\  $$$$$$\   $$$$$$\        
$$  _____|$$  __$$\ $$  __$$\       
$$ |      $$ /  \__|$$ /  \__|      
$$$$$\    \$$$$$$\  $$$$$$$\        
$$  __|    \____$$\ $$  __$$\       
$$ |      $$\   $$ |$$ /  $$ |      
$$$$$$$$\ \$$$$$$  | $$$$$$  |      
\________| \______/  \______/
Destructuring (Hủy diệt)
  let [...rest] = [10, 20, 30, 40, 50]; // rest = [10, 20, 30, 40, 50]

  let [a, b] = [10, 20]; // a = 10, b =  20
Computed (Tính toán)
  const param = "size";
  const config = {
    [param]: 12
  };
  // config: {size: 12}
Shorthand (Tốc ký)
  var keyName = 12;

  //PRE ES6
  var obj = {
    keyName: keyName
  };

  //ES6 Object property shorthand
  var obj = {
    keyName
  };

  // obj: {keyName: 12}
Spread (Lây lan)
  const numbers = [1, 2, 3];
  
  function sum(x, y, z) {
    return x + y + z;
  }

  sum(...numbers) // 6
view raw es6.md hosted with ❤ by GitHub
______           _                       
|  ___|         | |                      
| |_ ___  _ __  | |     ___   ___  _ __  
|  _/ _ \| '__| | |    / _ \ / _ \| '_ \ 
| || (_) | |    | |___| (_) | (_) | |_) |
\_| \___/|_|    \_____/\___/ \___/| .__/ 
                                  | |    
                                  |_|
    ____             _     
   / __ )____ ______(_)____
  / __  / __ `/ ___/ / ___/
 / /_/ / /_/ (__  ) / /__  
/_____/\__,_/____/_/\___/
  • The for loop:

    for (let index=0; index < someArray.length; index++) {
      const elem = someArray[index];
      // ···
    }
    
    More
    - ES1
    - Work with async/await
    - Work with `continue`
    - Work with `break`
    
  • The for-in loop:

    for (const key in someArray) {
      console.log(key);
    }
    
    More
    - ES1
    - Work with async/await
    - Work with `continue`
    - Work with `break`
    - Work with Array, Object
    
  • The Array method .forEach():

    someArray.forEach((elem, index) => {
      console.log(elem, index);
    });
    
    More
    - ES5
    - Not support async/await
    - Not work with `continue` 
      - `Error: Illegal continue statement: no surrounding iteration statement`
    - Not work with `break`
      - `Error: Illegal break statement`
    
  • The for-of loop:

    for (const elem of someArray) {
      console.log(elem);
    }
    
    More
    - ES6
    - Work with async/await (Nên sử dụng)
    - Work with `continue`
    - Work with `break`
    
    ### value
    
    for (let value of data) {}
    
    ### index
    
    for (let [index, value] of data.entries()) {}
    
    for (let index of arr.keys()) {}
    
    ### key value
    
    const myMap = new Map().set(false, 'no').set(true, 'yes');
    for (const [key, value] of myMap) {}
    
______           _                   
|  ___|         | |                  
| |_ ___  _ __  | | ___   ___  _ __  
|  _/ _ \| '__| | |/ _ \ / _ \| '_ \ 
| || (_) | |    | | (_) | (_) | |_) |
\_| \___/|_|    |_|\___/ \___/| .__/ 
                              | |    
                              |_|
                                                                                
   ___                       _____              _ __ 
  / _ | ___ __ _____  ____ _/_/ _ |_    _____ _(_) /_
 / __ |(_-</ // / _ \/ __//_// __ | |/|/ / _ `/ / __/
/_/ |_/___/\_, /_//_/\__/_/ /_/ |_|__,__/\_,_/_/\__/ 
          /___/
Data
const promiseFn = (n = 1) => new Promise((res, rej) =>  setTimeout(() => res(n), 1000 * n));

const array = [{
  id: 1,
  name: 'Nikolai'
},{
  id: 5,
  name: 'Wiliam'
}];

const object = {
  id: 5,
  name: 'Wiliam'
};
For basic - async/await
const run = async (data) => {
    for (let i = 0; i < data.length; ++i) {
        await promiseFn();
        console.log(data[i]);
    }
    console.log('this will print last');
}
  
run(array);

> { id: 1, name: "Nikolai" }
> { id: 5, name: "Wiliam" }
> "this will print last"
For of - async/await
const run = async (data) => {
  for (let item of data) {
    await promiseFn();
    console.log(item);
  }
  console.log('this will print last');
}
  
run(array);

> { id: 1, name: "Nikolai" }
> { id: 5, name: "Wiliam" }
> "this will print last"
For in - async/await
const run = async (data) => {
  for (let key in data) {
    await promiseFn();
    console.log(key, data[key]);
  }
  console.log('this will print last');
}

Array

run(array);

> "0" { id: 1, name: "Nikolai" }
> "1" { id: 5, name: "Wiliam" }
> "this will print last"

Object

run(object);

> "id" 5
> "name" "Wiliam"
> "this will print last"
for await (variable of iterable) - async/await
const promiseArr = [1,2,3,4].map(m => promiseFn(m));

const run = async () => {
    for await (let item of promiseArr) {
        console.log(item);
    }
    console.log('this will print last');
}
  
run();
  
// 1
// 2
// 3
// 4
// "this will print last"
Tốc độ của các vòng lặp
const arr = new Array(100).fill(Math.random());

// 01 - nhanh nhất
let dw = 0;
console.time('Do while');
do { dw++; } while(dw < arr.length)
console.timeEnd('Do while');

// 02
console.time('For');
for(let i = 0; i < arr.length; i++) { }
console.timeEnd('For');

// 03
let w = 0
console.time('While');
while(w < arr.length) { w ++ }
console.timeEnd('While');

// 04
console.time('ForEach');
arr.forEach(() => {})
console.timeEnd('ForEach');

// 05
console.time('For Of');
for(let item of arr) { }
console.timeEnd('For Of');

// 06 - chậm nhất
console.time('For In');
for(let item in arr) { }
console.timeEnd('For In');
view raw for-loop.md hosted with ❤ by GitHub
 _____                             _                 
|  ___|                           (_)                
| |____  ___ __  _ __ ___  ___ ___ _  ___  _ __  ___ 
|  __\ \/ / '_ \| '__/ _ \/ __/ __| |/ _ \| '_ \/ __|
| |___>  <| |_) | | |  __/\__ \__ \ | (_) | | | \__ \
\____/_/\_\ .__/|_|  \___||___/___/_|\___/|_| |_|___/
          | |                                        
          |_|
                                             ___   ___   ____  ___    __   _____  ___   ___   __  
                                            / / \ | |_) | |_  | |_)  / /\   | |  / / \ | |_) ( (` 
                                            \_\_/ |_|   |_|__ |_| \ /_/--\  |_|  \_\_/ |_| \ _)_)
Comma operator (,)
// Luôn lấy giá trị sau cùng
let x = 1;

(x++, x) // 2

(2, 3) // 3
in
const object1 = {
  prop: 'exists'
};

"prop" in object1 // true
Unary plus (+)
// string to number
+'1' // 1
Non-null assertion operator !.
// Toán tử xác nhận không null
<div *ngIf="hero">
  The hero's name is {{hero!.name}}
</div>
Do not use ~~ to truncate numbers to integers
// Do not use ~~x to truncate numbers to integers
~~2.6 // 2
// use Math.trunc() instead
Math.trunc(2.6) // 2
Addition assignment += Toán tử gán phép cộng
// x = x + 2; 
// x += 2
1 += 2 // 3;
1 += true // 2;
1 += false // 1;
1 += 'food' // '1food'

// BigInt + BigInt 
1n += 2n // 3n;
Subtraction assignment -= Toán tử gán phép trừ
let a = 3;
a = a - 2; // 1
a -= 2 // 1
Remainder assignment %= Toán tử gán phần dư
let a = 3;
a %= 2; // 1
a %= 3 // 0
Nullish coalescing operator ?? Toán tử kết hợp nullish
// Same
console.log(null ?? 'default string');
console.log(undefined ?? 'default string');
console.log(null || 'default string');
console.log(undefined || 'default string');

// "default string"
// "default string"
// "default string"
// "default string"


// Different
console.log(0 ?? 'default string');
console.log(false ?? 'default string');
console.log(0 || 'default string');
console.log(false || 'default string');

// 0
// false
// "default string"
// "default string"
Nullish coalescing assignment ??= Toán tử gán nullish kết hợp
   - Được sử dụng để gán giá trị cho biến nếu biến đó  null. 
   - Nếu biến không phải  null, giá trị của biến sẽ không bị thay đổi. 
const a = { duration: 50 };
a.speed ??= 25; // a.speed = 25
a.duration ??= 10 // a.duration = 50
Logical OR assignment ||= Toán tử gán logic OR chỉ gán nếu x là falsy
const a = { duration: 50, title: '' };
a.duration ||= 10; // 50
a.title ||= 'title is empty.'; // "title is empty."
Logical AND assignment (&&=) Toán tử gán AND chỉ gán nếu xlà true
   - Được sử dụng để kiểm tra một điều kiện  gán giá trị cho biến dựa trên kết quả của điều kiện đó. 
   - Nếu điều kiện  true, giá trị gán sẽ được thực hiện. 
   - Nếu điều kiện  false, giá trị gán sẽ không được thực hiện. 
let a = 1;
let b = 0;
a &&= 2; // 2
b &&= 2; // 0
Destructuring assignment
let a, b, rest;

[a, b, ...rest] = [10, 20, 30, 40, 50];

// rest: [30, 40, 50]
yield
function* foo(index) {
  yield index;
  yield index+1;
  yield index+2;
  // while (index < 4) {
  //   yield index;
  //   index++;
  // }
}

const iterator = foo(1); // Gọi vào hàm foo một lần duy nhất

console.log(iterator.next().value); // Output: 1 chạy yield 1
console.log(iterator.next().value); // Output: 2 chạy yield 2
console.log(iterator.next().value); // Output: 3 chạy yield 3
yield*
function* func1() {
  yield 42;
  yield 43;
}

function* func2() {
  yield* func1(); // yield* handle lại yield
}

const iterator = func2();

console.log(iterator.next().value); // 42
console.log(iterator.next().value); // 43

https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators

 _____                                    __  _____                       _   
(  _  )                                  /  )(  _  )                   _ ( )_ 
| (_) |  ___  _   _   ___     ___      /' /' | (_) | _   _   _    _ _ (_)| ,_)
|  _  |/',__)( ) ( )/' _ `\ /'___)   /' /'   |  _  |( ) ( ) ( ) /'_` )| || |  
| | | |\__, \| (_) || ( ) |( (___  /' /'     | | | || \_/ \_/ |( (_| || || |_ 
(_) (_)(____/`\__, |(_) (_)`\____)(_/'       (_) (_)`\___x___/'`\__,_)(_)`\__)
             ( )_| |                                                          
             `\___/'                                                          
Async
async function f() {
  return 1; 
}

f().then(alert); // 1 
Await
async function f() {
  let promise = new Promise((resolve, reject) => {
    setTimeout(() => resolve("done!"), 1000)
  });
  let result = await promise; // wait until the promise resolve
  alert(result); // done!
}
f();
view raw async-await.md hosted with ❤ by GitHub
______                    _          
| ___ \                  (_)         
| |_/ / __ ___  _ __ ___  _ ___  ___ 
|  __/ '__/ _ \| '_ ` _ \| / __|/ _ \
| |  | | | (_) | | | | | | \__ \  __/
\_|  |_|  \___/|_| |_| |_|_|___/\___|
Promise.all
// 1 in 3 promise reject return catch
Promise.all([promise1, promise2, promise3])
Promise.race
// Lấy promise resolve đầu tiên
// Không làm việc với reject
const promise1 = new Promise((resolve) => setTimeout(resolve, 200, 'slow'));
const promise2 = new Promise((resolve) => setTimeout(resolve, 100, 'quick'));

Promise.race([promise1, promise2]).then((value) => console.log(value));

// ouput: "quick"
Promise.allSettled
// Return all resolve + reject 
const promise1 = Promise.resolve(3);
const promise2 = new Promise((resolve, reject) => setTimeout(reject, 100, 'foo'));

Promise.allSettled([promise1, promise2]).then((res) => {
  res.forEach((f) => console.log(f))
});

// { status: "fulfilled", value: 3 }
// { status: "rejected", reason: "foo" }
Promise.any
// Lấy promise resolve đầu tiên
// Vẫn trả kết quả khi reject
const promise1 = Promise.reject(0);
const promise2 = new Promise((resolve) => setTimeout(resolve, 100, 'quick'));
const promise3 = new Promise((resolve) => setTimeout(resolve, 500, 'slow'));

Promise.any([promise1, promise2, promise3]).then((value) => console.log(value));

// ouput: "quick"
Chaining: then - catch - finally
function checkMail() {
  return new Promise((resolve, reject) => {
    return Math.random() > 0.5 ? resolve('Mail has arrived') : reject(new Error('Failed to arrive'))
  });
}

checkMail()
  .then((mail) => {
    console.log(mail);
  })
  .catch((err) => {
    console.error(err);
  })
  .finally(() => {
    console.log('Experiment completed');
  });
  
// Error: Failed to arrive
// "Experiment completed"
  
State
  • Pending (Đang chờ xử lý) - process is not complete (Quá trình chưa hoàn tất)

  • Fulfilled (Hoàn thành) - operation is successful (Thao tác thành công)

  • Rejected (Bị từ chối) - an error occurs (Xảy ra lỗi)

    promise-status

view raw promise.md hosted with ❤ by GitHub
 _____                           
/  __ \                          
| /  \/ __ _ _ ____   ____ _ ___ 
| |    / _` | '_ \ \ / / _` / __|
| \__/\ (_| | | | \ V / (_| \__ \
 \____/\__,_|_| |_|\_/ \__,_|___/
Details
let canvas = document.createElement('canvas') as HTMLCanvasElement;

canvas.width = 1280;
canvas.height = 720;

// Get a 2D drawing context for the canvas.
const ctx = canvas.getContext('2d', { willReadFrequently: true }) as CanvasRenderingContext2D;

// Draw image from (video, canvas, image element origin)
ctx.drawImage(videoEl, 0, 0, canvas.width, canvas.height);

// Canvas to base64
canvas.toDataURL()
// or
canvas.toDataURL(type, quality);
// or
canvas.toDataURL(`image/${fileName?.split('.')?.slice(-1)?.toString()}`);

// Canvas to URL blob
canvas.toBlob((blob: any) => {
  const url = URL.createObjectURL(blob)
});

// Clean and reset canvas
const context = dom.canvas.getContext('2d', { willReadFrequently: true }) as CanvasRenderingContext2D;
context.clearRect(0, 0, dom.canvas.width, dom.canvas.height);
Draw image into canvas
 
 /**
 * DRAW_IMAGE
 * @param canvas 
 * @param image 
 */
export const DRAW_IMAGE = (canvas: HTMLCanvasElement, image: ImageBitmap | any) => {
  canvas.width = image.width;
  canvas.height = image.height;
  const ctx = canvas.getContext('2d') as CanvasRenderingContext2D;
  ctx.drawImage(image, 0, 0, canvas.width, canvas.height);
}
view raw canvas.md hosted with ❤ by GitHub

Related Posts:

0 nhận xét:

Post a Comment

 

BACK TO TOP

Xuống cuối trang