Convert từ string
sang số
, việc này các bạn đã làm không ít lần phải không?
Có khá là nhiều cách để convert như:
- parseInt(x)
- parseFloat(x)
- Number(x)
- +x
- ~~x
Bạn có thể quen thuộc với parseInt
, parseFloat
, Number
và tên của họ cho thấy khá rõ những gì họ làm. Toán tử unary plus
và toán tử Bitwise NOT
(dấu ngã kép ~~
) ít khi được chúng ta dùng.
Hãy cùng tìm hiểu về sự khác biệt khi convert
string thành số của 5 cách trên nhé
1. Type of the conversion
Kiểu convert
1 2 3 4 5 6 | <span class="token function">parseInt</span><span class="token punctuation">(</span><span class="token string">"1.3"</span><span class="token punctuation">)</span> <span class="token comment">// 1</span> <span class="token function">parseInt</span><span class="token punctuation">(</span><span class="token string">"1"</span><span class="token punctuation">)</span> <span class="token comment">// 1</span> |
Sự khác biệt rõ ràng nhất là loại kết quả trả về của mỗi cách. parseInt
sẽ luôn chuyển đổi thành một Integer
.
Sử dụng ~~
cũng sẽ luôn trả về 1 Integer
1 2 3 4 5 6 | <span class="token operator">~</span><span class="token operator">~</span><span class="token string">"1.0"</span> <span class="token comment">// 1</span> <span class="token operator">~</span><span class="token operator">~</span><span class="token string">"1.3"</span> <span class="token comment">// 1</span> |
parseFloat
, +
và function Number
sẽ trả về Integer
nếu có thể, và sẽ trả về Float
trong các trường hợp còn lại
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 | <span class="token function">Number</span><span class="token punctuation">(</span><span class="token string">"1.0"</span><span class="token punctuation">)</span> <span class="token comment">// 1</span> <span class="token function">Number</span><span class="token punctuation">(</span><span class="token string">"1.4"</span>'<span class="token punctuation">)</span> <span class="token comment">// 1.4</span> <span class="token function">parseFloat</span><span class="token punctuation">(</span><span class="token string">"1.0"</span><span class="token punctuation">)</span> <span class="token comment">// 1</span> <span class="token function">ParseFloat</span><span class="token punctuation">(</span><span class="token string">"1.4"</span><span class="token punctuation">)</span> <span class="token comment">// 1.4</span> <span class="token operator">+</span><span class="token string">"1.0"</span> <span class="token comment">// 1</span> <span class="token operator">+</span><span class="token string">"1.4"</span> <span class="token comment">// 1.4</span> |
2. Type of the operand
Tất cả các cách trên đều có thể nhận đầu vào là một string. Tuy nhiên nếu đầu vào của nó không phải là một string thì sao?
parseInt
và parseFloat
sẽ luôn trả về NaN
cho mọi input không phải string
1 2 3 4 5 6 7 8 9 10 11 12 | <span class="token function">parseInt</span><span class="token punctuation">(</span><span class="token boolean">true</span><span class="token punctuation">)</span><span class="token punctuation">;</span> <span class="token comment">// NaN</span> <span class="token function">parseInt</span><span class="token punctuation">(</span><span class="token punctuation">{</span><span class="token punctuation">}</span><span class="token punctuation">)</span><span class="token punctuation">;</span> <span class="token comment">// NaN</span> <span class="token function">parseInt</span><span class="token punctuation">(</span><span class="token keyword">null</span><span class="token punctuation">)</span><span class="token punctuation">;</span> <span class="token comment">// NaN</span> <span class="token function">parseInt</span><span class="token punctuation">(</span>undefined<span class="token punctuation">)</span><span class="token punctuation">;</span> <span class="token comment">// NaN</span> |
Number
, +
và ~~
có thể convert
các giá trị boolean
, trả về 1 nếu đầu vào là true
, 0 nếu đầu vào là false
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 | <span class="token function">Number</span><span class="token punctuation">(</span><span class="token boolean">true</span><span class="token punctuation">)</span> <span class="token comment">// 1</span> <span class="token operator">+</span><span class="token boolean">true</span> <span class="token comment">// 1</span> <span class="token function">Number</span><span class="token punctuation">(</span><span class="token boolean">false</span><span class="token punctuation">)</span> <span class="token comment">// 0</span> <span class="token operator">+</span><span class="token boolean">false</span> <span class="token comment">// 0</span> <span class="token operator">~</span><span class="token operator">~</span><span class="token boolean">true</span> <span class="token comment">// 1</span> <span class="token operator">~</span><span class="token operator">~</span><span class="token boolean">false</span> <span class="token comment">//0</span> |
và chúng sẽ trả về 0
cho giá trị đầu vào là null
1 2 3 4 5 6 7 | <span class="token function">Number</span><span class="token punctuation">(</span><span class="token keyword">null</span><span class="token punctuation">)</span> <span class="token comment">// 0</span> <span class="token operator">+</span><span class="token keyword">null</span> <span class="token comment">// 0</span> <span class="token operator">~</span><span class="token operator">~</span><span class="token keyword">null</span> <span class="token comment">// 0</span> |
Khi giá trị đầu vào là undefined
thì Number
và +
sẽ trả về NaN
còn ~~
sẽ tả về 0
3. Invalid conversions
Khi mà dữ liệu đầu vào không đúng (định dạng sai) thì chúng ta sẽ thấy nhiều hơn sự khá biệt giữa cách cách trên.
parseInt và parseFloat sẽ convert nhiều nhất có thể, cho đến khi chúng tìm thấy một phần tử không thể conver.
1 2 3 4 5 6 | <span class="token function">parseInt</span><span class="token punctuation">(</span><span class="token string">"2.3test45"</span><span class="token punctuation">)</span> <span class="token comment">// 2</span> <span class="token function">parseFloat</span><span class="token punctuation">(</span><span class="token string">"2.3test45"</span><span class="token punctuation">)</span> <span class="token comment">// 2.34</span> |
Number
và +
sẽ trả về NaN
nếu đầu vào không thể chuyển đổi. Như mọi khi, ~~
trả về một số nguyên – 0
.
Cách mỗi thao tác xử lý với một chuỗi rỗng cũng thú vị. Tất cả đều trả về 0 ngoại trừ parseInt và parseFloat trả về NaN
Có 1 điều khá là thú vị, khi convert một chuỗi trống. parseInt
và parseFloat
sẽ trả về NaN
còn lại sẽ trả về 0
1 2 3 4 5 6 7 8 9 10 | <span class="token function">Number</span><span class="token punctuation">(</span><span class="token string">''</span><span class="token punctuation">)</span> <span class="token comment">// 0</span> <span class="token operator">+</span><span class="token string">''</span> <span class="token comment">// 0</span> <span class="token operator">~</span><span class="token operator">~</span><span class="token string">""</span> <span class="token comment">// 0</span> <span class="token function">parseInt</span><span class="token punctuation">(</span><span class="token string">""</span><span class="token punctuation">)</span> <span class="token comment">// NaN</span> |
4. Exponents, hex and other bases
parseInt
có tính năng khá là hay, khi bạn có thể truyền thêm tham số về hệ
(base) như tham số thứ 2. Mặc định là hệ cơ số 10
1 2 3 4 5 6 | <span class="token function">parseInt</span><span class="token punctuation">(</span><span class="token string">'a'</span><span class="token punctuation">,</span> <span class="token number">16</span><span class="token punctuation">)</span> <span class="token comment">// 10</span> <span class="token function">parseInt</span><span class="token punctuation">(</span><span class="token string">'11'</span><span class="token punctuation">,</span> <span class="token number">2</span><span class="token punctuation">)</span> <span class="token comment">// 3</span> |
Còn với Number
, +
và ~~
: thì nó không hoạt động
1 2 3 4 5 6 7 | <span class="token function">Number</span><span class="token punctuation">(</span><span class="token string">'a'</span><span class="token punctuation">,</span> <span class="token number">16</span><span class="token punctuation">)</span> <span class="token comment">// NaN</span> <span class="token operator">+</span><span class="token string">"a"</span> <span class="token comment">// NaN</span> <span class="token operator">~</span><span class="token operator">~</span><span class="token string">"a"</span> <span class="token comment">// NaN</span> |
Mặt khác, parseInt
không thể chuyển đổi string với ký hiệu số mũ, trong khi tất cả những cách khác thì có thể. Chính xác hơn, parseInt
sẽ dừng ở ký tự không phải là số đầu tiên, trả về kết quả không mong muốn:
1 2 3 4 5 6 7 8 9 | <span class="token operator">+</span><span class="token string">"2e3"</span> <span class="token comment">// 2000</span> <span class="token operator">~</span><span class="token operator">~</span><span class="token string">"2e3"</span> <span class="token comment">// 2000</span> <span class="token function">Number</span><span class="token punctuation">(</span><span class="token string">"2e3"</span><span class="token punctuation">)</span> <span class="token comment">// 2000</span> <span class="token function">parseInt</span><span class="token punctuation">(</span><span class="token string">"2e3"</span><span class="token punctuation">)</span> <span class="token comment">// 2</span> |
Không giống với số mũ, parseInt
hoạt động đúng với hệ cơ số 8:
1 2 3 4 5 6 7 8 9 | <span class="token function">Number</span><span class="token punctuation">(</span><span class="token string">"0xa"</span><span class="token punctuation">)</span> <span class="token comment">// 10</span> <span class="token operator">+</span><span class="token string">"0xa"</span> <span class="token comment">// 10</span> <span class="token operator">~</span><span class="token operator">~</span><span class="token string">"0xa"</span> <span class="token comment">// 10</span> <span class="token function">parseInt</span><span class="token punctuation">(</span><span class="token string">"0xa"</span><span class="token punctuation">)</span> <span class="token comment">// 10</span> |