Những lỗi thường gặp về JavaScript
Chương này chỉ ra một số lỗi JavaScript phổ biến.
Vô tình sử dụng toán tử gán
Các chương trình JavaScript có thể tạo ra kết quả không mong muốn nếu lập trình viên vô tình sử dụng toán tử gán ( =
), thay vì toán tử so sánh ( ==
) trong câu lệnh if.
Câu lệnh if
này trả về false
(như mong đợi) vì x không bằng 10:
let x = 0;
if (x == 10)
Hãy tự mình thử » Câu lệnh if
này trả về true
(có thể không như mong đợi), vì 10 là đúng:
let x = 0;
if (x = 10)
Hãy tự mình thử » Câu lệnh if
này trả về false
(có thể không như mong đợi), vì 0 là sai:
let x = 0;
if (x = 0)
Hãy tự mình thử »Một phép gán luôn trả về giá trị của phép gán.
Mong đợi sự so sánh lỏng lẻo
Trong so sánh thông thường, kiểu dữ liệu không quan trọng. Câu lệnh if
này trả về true:
let x = 10;
let y = "10";
if (x == y)
Hãy tự mình thử » Trong so sánh chặt chẽ, loại dữ liệu có vấn đề. Câu lệnh if
này trả về false:
let x = 10;
let y = "10";
if (x === y)
Hãy tự mình thử » Một sai lầm phổ biến là quên rằng các câu lệnh switch
sử dụng sự so sánh chặt chẽ:
case switch
này sẽ hiển thị một cảnh báo:
let x = 10;
switch(x) {
case 10: alert("Hello");
}
Hãy tự mình thử » case switch
này sẽ không hiển thị cảnh báo:
let x = 10;
switch(x) {
case "10": alert("Hello");
}
Hãy tự mình thử » Sự cộng và nối khó hiểu
Ngoài ra là về việc thêm số .
Nối có nghĩa là thêm các chuỗi .
Trong JavaScript cả hai thao tác đều sử dụng cùng một toán tử +
.
Vì lý do này, việc cộng một số dưới dạng số sẽ tạo ra kết quả khác với việc cộng một số dưới dạng chuỗi:
let x = 10;
x = 10 + 5; //
Now x is 15
let y = 10;
y += "5";
// Now y is "105"
Hãy tự mình thử »Khi cộng hai biến, có thể khó dự đoán kết quả:
let x = 10;
let y = 5;
let z = x + y; // Now z is 15
let x = 10;
let y = "5";
let z = x + y; // Now z is "105"
Hãy tự mình thử »Hiểu lầm phao
Tất cả các số trong JavaScript được lưu trữ dưới dạng số dấu phẩy động 64 bit (Floats).
Tất cả các ngôn ngữ lập trình, bao gồm cả JavaScript, đều gặp khó khăn với các giá trị dấu phẩy động chính xác:
let x = 0.1;
let y = 0.2;
let z = x + y
// the result in z will not be 0.3
Hãy tự mình thử »Để giải quyết vấn đề trên, nó giúp nhân và chia:
Phá vỡ một chuỗi JavaScript
JavaScript sẽ cho phép bạn chia một câu lệnh thành hai dòng:
Tuy nhiên, việc ngắt câu lệnh ở giữa chuỗi sẽ không có tác dụng:
Bạn phải sử dụng "dấu gạch chéo ngược" nếu bạn phải ngắt câu lệnh trong chuỗi:
Đặt sai dấu chấm phẩy
Do dấu chấm phẩy bị đặt sai vị trí, khối mã này sẽ thực thi bất kể giá trị của x:
if (x == 19);
{
// code block
}
Hãy tự mình thử »Phá vỡ một tuyên bố hoàn trả
Hành vi mặc định của JavaScript là tự động đóng một câu lệnh ở cuối dòng.
Vì điều này, hai ví dụ này sẽ trả về cùng một kết quả:
JavaScript cũng sẽ cho phép bạn chia một câu lệnh thành hai dòng.
Vì điều này, ví dụ 3 cũng sẽ trả về kết quả tương tự:
Tuy nhiên, điều gì sẽ xảy ra nếu bạn chia câu lệnh return thành hai dòng như thế này:
Hàm sẽ trả về undefined
!
Tại sao? Bởi vì JavaScript nghĩ ý bạn là:
Giải trình
Nếu một tuyên bố không đầy đủ như:
let
JavaScript sẽ cố gắng hoàn thành câu lệnh bằng cách đọc dòng tiếp theo:
power = 10;
Nhưng vì tuyên bố này đã hoàn tất:
return
JavaScript sẽ tự động đóng nó như thế này:
return;
Điều này xảy ra vì câu lệnh đóng (kết thúc) bằng dấu chấm phẩy là tùy chọn trong JavaScript.
JavaScript sẽ đóng câu lệnh return ở cuối dòng vì đây là câu lệnh hoàn chỉnh.
Không bao giờ phá vỡ câu lệnh return.
Truy cập mảng với các chỉ mục được đặt tên
Nhiều ngôn ngữ lập trình hỗ trợ mảng có chỉ mục được đặt tên.
Mảng có chỉ mục được đặt tên được gọi là mảng kết hợp (hoặc băm).
JavaScript không hỗ trợ các mảng có chỉ mục được đặt tên.
Trong JavaScript, mảng sử dụng các chỉ mục được đánh số :
Ví dụ
const person = [];
person[0] = "John";
person[1] = "Doe";
person[2] = 46;
person.length;
// person.length will return 3
person[0];
// person[0] will return "John"
Hãy tự mình thử »Trong JavaScript, các đối tượng sử dụng các chỉ mục được đặt tên .
Nếu bạn sử dụng chỉ mục được đặt tên, khi truy cập vào một mảng, JavaScript sẽ xác định lại mảng đó thành một đối tượng tiêu chuẩn.
Sau khi tự động xác định lại, các phương thức và thuộc tính mảng sẽ tạo ra kết quả không xác định hoặc không chính xác:
Ví dụ:
const person = [];
person["firstName"] = "John";
person["lastName"] = "Doe";
person["age"] = 46;
person.length; // person.length will
return 0
person[0];
// person[0] will return undefined
Hãy tự mình thử »Kết thúc định nghĩa bằng dấu phẩy
Dấu phẩy ở cuối trong định nghĩa đối tượng và mảng là hợp pháp trong ECMAScript 5.
Ví dụ về đối tượng:
person = {firstName:"John", lastName:"Doe", age:46,}
Ví dụ về mảng:
points = [40, 100, 1, 5, 25, 10,];
CẢNH BÁO !!
Internet Explorer 8 sẽ gặp sự cố.
JSON không cho phép dấu phẩy ở cuối.
JSON:
person = {"firstName":"John", "lastName":"Doe", "age":46}
JSON:
points = [40, 100, 1, 5, 25, 10];
Không xác định là không rỗng
Các đối tượng, biến, thuộc tính và phương thức JavaScript có thể không được undefined
.
Ngoài ra, các đối tượng JavaScript trống có thể có giá trị null
.
Điều này có thể gây khó khăn một chút cho việc kiểm tra xem một đối tượng có trống không.
Bạn có thể kiểm tra xem một đối tượng có tồn tại hay không bằng cách kiểm tra xem loại đó có phải là undefined
hay không:
Nhưng bạn không thể kiểm tra xem một đối tượng có phải là null
hay không, vì điều này sẽ gây ra lỗi nếu đối tượng undefined
:
Không đúng:
if (myObj === null)
Để giải quyết vấn đề này, bạn phải kiểm tra xem một đối tượng có phải là null
hay không và không undefined
.
Nhưng điều này vẫn có thể gây ra lỗi:
Không đúng:
if (myObj !== null && typeof myObj
!== "undefined")
Vì điều này, bạn phải kiểm tra not undefined
trước khi có thể kiểm tra not null
: