Khi dùng parseInt() chỉ với một tham số, các linter (JSLint, JSHint, ESLint) sẽ cảnh báo "Missing radix parameter". Đây là cảnh báo quan trọng để tránh hành vi ép kiểu ngầm định gây bug khó tìm.
Chữ ký hàm parseInt
parseInt(string, radix);
- string: Giá trị cần parse. Nếu không phải string, JS tự chuyển bằng
ToString(). Khoảng trắng đầu được bỏ qua. - radix (cơ số): Số nguyên từ 2 đến 36. Bắt buộc nên cung cấp.
Tại sao cần radix? — Hành vi "ma thuật" khi thiếu tham số
Nếu không truyền radix, JavaScript tự đoán cơ số theo tiền tố chuỗi:
| Tiền tố chuỗi | Radix được giả định | Hệ cơ số |
|---|---|---|
"0x..." hoặc "0X..." | 16 | Hexadecimal |
"0..." (bắt đầu bằng 0) | 8 | Octal (Deprecated) |
Khác (vd: "123", " 45") | 10 | Decimal |
Ví dụ nguy hiểm
// Không truyền radix - KHÔNG AN TOÀN
parseInt("08"); // Kết quả: 0 (ES5 strict) hoặc 8 (non-strict) — do được hiểu là octal!
parseInt("09"); // 0 (octal không có chữ số 9)
parseInt("010"); // 8 (octal 10 = decimal 8)
// Truyền radix = 10 - AN TOÀN, DỰ ĐOÁN ĐƯỢC
parseInt("08", 10); // 8 ✓
parseInt("09", 10); // 9 ✓
parseInt("010", 10); // 10 ✓
// Hexadecimal - vẫn cần radix 16 để rõ ràng
parseInt("0xFF", 16); // 255 ✓
Tại sao octal bị deprecated?
- Trong ES5 strict mode, chuỗi bắt đầu bằng
"0"không còn được coi là octal — trả về 0 cho "08", "09". - ES2015+ khuyến cáo luôn truyền radix để code hành vi nhất quán giữa strict/non-strict mode.
- Nhiều bug thực tế do nhập liệu người dùng (ngày/tháng "08", "09") bị parse sai thành 0.
Cách sửa lỗi lint
// ❌ Sai - Missing radix
const num = parseInt(userInput);
// ✅ Đúng - Luôn truyền radix 10 cho số thập phân
const num = parseInt(userInput, 10);
// ✅ Cho hex (nếu chắc chắn input có 0x)
const hex = parseInt(hexString, 16);
// ✅ Hàm wrapper an toàn (khuyên dùng)
const parseInt10 = (str) => parseInt(str, 10);
const num = parseInt10(userInput);
Cấu hình ESLint
Rule liên quan: radix (mặc định: error)
// .eslintrc.json
{
"rules": {
"radix": "error" // Bắt buộc truyền radix
}
}
Lưu ý thêm
Number()hoặc+str(unary plus) cũng chuyển string thành số nhưng không parse từng ký tự —Number("123abc")trả vềNaN, trong khiparseInt("123abc", 10)trả về123.- Dùng
parseFloat()cho số thực, cũng nên truyền radix (dù ít gặp vấn đề octal). - Radix hợp lệ: 2–36. Truyền ngoài phạm vi →
NaN.
Tóm tắt
Luôn viết parseInt(str, 10) cho số thập phân. Cảnh báo "Missing radix parameter" không phải lỗi chạy, nhưng là dấu hiệu code dễ vỡ. Việc thêm radix tốn 3 ký tự nhưng giúp tránh hàng giờ debug bug nhập liệu "08"/"09".