0
0
Lập trình
NM

JavaScript Nâng Cao - Kỳ 29: Khám Phá Tham Chiếu, Kế Thừa và Ý Nghĩa Của Mảng

Đăng vào 4 tuần trước

• 4 phút đọc

JavaScript Nâng Cao - Kỳ 29: Khám Phá Tham Chiếu, Kế Thừa và Ý Nghĩa Của Mảng

Giới Thiệu

Có một câu nói vui như thế này: "Trên đời chỉ có thứ nhiều người chửi và thứ không ai thèm dùng." Javascript là một ví dụ điển hình cho điều này. Mặc dù nó có nhiều tính năng thú vị, nhưng cũng có nhiều khía cạnh gây đau đầu cho lập trình viên. Trong bài viết này, chúng ta sẽ cùng nhau tìm hiểu một cách chi tiết qua những ví dụ cụ thể để làm rõ hơn về Javascript.

Series này là một hành trình dài, và mình không chắc nó sẽ kéo dài bao lâu. Tuy nhiên, để giúp các bạn dễ dàng theo dõi, mình sẽ giải thích lại các lý thuyết trong bài một cách tỉ mỉ nhất, và có thể sẽ tái giải thích nhiều lần để bạn có thể nắm vững kiến thức hơn.

Vậy thì chúng ta hãy bắt đầu! GÉT GÔ 🚀

Nếu bạn có bất kỳ câu hỏi nào, hãy đừng ngần ngại bình luận dưới bài viết này nhé. Hoặc chỉ cần để lại một bình luận chào mình cũng đã là động lực lớn để mình hoàn thành series này. Cảm ơn các bạn rất nhiều. 🤗

1. Tham Chiếu và Giá Trị Mặc Định Trong Hàm

Ví dụ 1:

Hãy xem đoạn code dưới đây và cho biết output của nó là gì:

javascript Copy
const person = {
 name: "Lydia Hallie",
 hobbies: ["coding"]
};

function addHobby(hobby, hobbies = person.hobbies) {
 hobbies.push(hobby);
 return hobbies;
}

addHobby("running", []);
addHobby("dancing");
addHobby("baking", person.hobbies);

console.log(person.hobbies);
  • A: ['coding']
  • B: ['coding', 'dancing']
  • C: ['coding', 'dancing', 'baking']
  • D: ['coding', 'running', 'dancing', 'baking']

Đáp Án:

Đáp án của câu hỏi này là: C - ['coding', 'dancing', 'baking'].

Phân Tích Chi Tiết:

Để hiểu rõ lý do đằng sau đáp án này, chúng ta phân tích từng lời gọi hàm addHobby:

  1. Lời gọi addHobby("running", []):

    • Mảng rỗng được truyền vào hàm, do đó "running" được thêm vào mảng rỗng này, nhưng không ảnh hưởng đến person.hobbies.
  2. Lời gọi `addHobby("dancing"):

    • Không có đối số thứ hai, hàm sử dụng giá trị mặc định person.hobbies, và "dancing" được thêm vào person.hobbies.
  3. Lời gọi addHobby("baking", person.hobbies):

    • Trực tiếp truyền person.hobbies, do đó "baking" cũng được thêm vào mảng này.

Kết quả cuối cùng là: person.hobbies sẽ chứa: ['coding', 'dancing', 'baking'].

2. Kế Thừa và Constructor Trong Class

Ví dụ 2:

Xem đoạn code dưới đây:

javascript Copy
class Bird {
 constructor() {
  console.log("I'm a bird. 🦢");
 }
}

class Flamingo extends Bird {
 constructor() {
  console.log("I'm pink. 🌸");
  super();
 }
}

const pet = new Flamingo();
  • A: I'm pink. 🌸
  • B: I'm pink. 🌸 I'm a bird. 🦢
  • C: I'm a bird. 🦢 I'm pink. 🌸
  • D: Nothing, we didn't call any method

Đáp Án:

Đáp án là: B - I'm pink. 🌸 I'm a bird. 🦢

Phân Tích:

  1. Khi tạo một instance mới của Flamingo, constructor của Flamingo được gọi, in ra "I'm pink. 🌸".
  2. Sau đó, super() được gọi, thực hiện constructor của lớp cha (Bird), và in ra "I'm a bird. 🦢".

Do đó, kết quả in ra là:

  • "I'm pink. 🌸"
  • "I'm a bird. 🦢"

3. Thao Tác Với Mảng và Hằng Số

Ví dụ 3:

Câu lệnh nào sẽ gây ra lỗi dưới đây:

javascript Copy
const emojis = ["🎄", "🎅🏼", "🎁", "⭐"];

/* 1 */ emojis.push("🦌");
/* 2 */ emojis.splice(0, 2);
/* 3 */ emojis = [...emojis, "🥂"];  
/* 4 */ emojis.length = 0;
  • A: 1
  • B: 1 và 2
  • C: 3 và 4
  • D: 3

Đáp Án:

Đáp án là: D

Giải Thích:

Dựa trên cách mà const hoạt động với các mảng:

  1. Câu lệnh 1 và 2 không gây lỗi vì chúng chỉ thay đổi nội dung của mảng, không gán lại.
  2. Câu lệnh 3 sẽ gây ra lỗi vì nó cố gắng gán lại giá trị cho emojis. Điều này không cho phép với biến được khai báo bằng const.
  3. Câu lệnh 4 thì hợp lệ vì nó chỉ thay đổi thuộc tính length của mảng mà không gán lại.

4. Iterator và Symbol.iterator

Ví dụ 4:

Ta cần định nghĩa gì vào object person để khi gọi [...person] sẽ cho kết quả là ['Lydia Hallie', 21]?

javascript Copy
const person = {
  name: "Lydia Hallie",
  age: 21
}

[...person] // ['Lydia Hallie', 21]
  • A: Nothing, object are iterable by default
  • B: *[Symbol.iterator]() { for (let x in this) yield* this[x] }
  • C: *[Symbol.iterator]() { for (let x in this) yield* Object.values(this) }
  • D: *[Symbol.iterator]() { for (let x in this) yield this }

Đáp Án:

Đáp án là: C

Phân Tích:

  1. Để khiến một object trở nên có thể lặp (iterable), ta cần định nghĩa phương thức Symbol.iterator.
  2. Phương thức này sẽ trả về một iterator object, thường được tạo bằng một generator function, sử dụng yield để trả về các giá trị.
  3. Đáp án C là chính xác khi sử dụng yield* Object.values(this) để lấy tất cả giá trị của object.

5. Truthy và Falsy Trong JavaScript

Ví dụ 5:

Output của đoạn mã dưới đây sẽ là gì:

javascript Copy
let count = 0;
const nums = [0, 1, 2, 3];

nums.forEach(num => {
 if (num) count += 1;
})

console.log(count);
  • A: 1
  • B: 2
  • C: 3
  • D: 4

Đáp Án:

Đáp án là: C - 3

Phân Tích:

  1. Trong mảng nums, chỉ có số 0 là falsy, còn lại (1, 2, 3) đều là truthy.
  2. Với mỗi phần tử, nếu nó là truthy, câu lệnh count += 1 sẽ được thực thi.
  3. Kết quả cuối cùng sẽ là 3 sau khi lặp qua tất cả các phần tử.

Hy vọng qua bài viết này, bạn đã hiểu rõ hơn về các chủ đề liên quan đến tham chiếu, kế thừa, mảng và nhiều khái niệm khác trong JavaScript. Nếu bạn có bất kỳ câu hỏi nào, hãy comment phía dưới nhé! Hẹn gặp lại bạn trong các kỳ sau của series JavaScript Nâng Cao!
source: viblo

Gợi ý câu hỏi phỏng vấn
Không có dữ liệu

Không có dữ liệu

Bài viết được đề xuất
Bài viết cùng tác giả

Bình luận

Chưa có bình luận nào

Chưa có bình luận nào