如果你问一个手机店的店员一种特定手机的价格,而他们说“九十九块九毛九”(即,$99.99),他们给了你一个实际的美元数字来表示你需要花多少钱才能买到它。如果你想两部这种手机,你可以很容易地心算这个值的两倍来得到你需要花费的$199.98。
如果同一个店员拿起另一部相似的手机说它是“免费的”(也许在用手比划引号),那么他们就不是在给你一个数字,而是你的花费($0.00)的另一种表达形式 —— “免费”这个词。
当你稍后问到这个手机是否带充电器时,回答可能仅仅是“是”或者“不”。
以同样的方式,当你在程序中表达一个值时,你根据你打算对这些值做什么来选择不同的表达形式。
在编程术语中值的这些不同的表达形式称为 类型。JavaScript中对这些所谓的 基本类型 值都有内建的类型:
- 但你需要做数学计算时,你需要一个
number
。 - 当你需要在屏幕上打印一个值时,你需要一个
string
(一个或多个字符,单词,句子)。 - 当你需要在你的程序中做决定时,你需要一个
boolean
(true
或false
)。
在源代码中直接包含的值称为 字面量。string
字面量被双引号"..."
或单引号('...'
)包围 —— 唯一的区别是风格上的偏好。number
和boolean
字面量用它们本身来表示(即,42
,true
,等等)。
考虑如下代码:
"I am a string";
'I am also a string';
42;
true;
false;
在string
/number
/boolean
值的类型以外,编程语言通常会提供 数组,对象,函数 等更多的类型。我们会在本章和下一章中讲解更多关于值和类型的内容。
类型间转换
如果你有一个number
但需要将它打印在屏幕上,那么你就需要将这个值转换为一个string
,在JavaScript中这种转换称为“强制转换”。类似地,如果某些人在一个电商网页的form中输入一系列数字,那么它是一个string
,但是如果你需要使用这个值去做数学运算,那么你就需要将它 强制转换 为一个number
。
为了在 类型 之间强制转换,JavaScript提供了几种不同的工具。例如:
var a = "42";
var b = Number( a );
console.log( a ); // "42"
console.log( b ); // 42
使用上面展示的Number(..)
(一个内建函数)是一种从任意其他类型到number
类型的 明确的 强制转换。这应当是相当直白的。
但是一个具有争议的话题是,当你试着比较两个还不是相同类型的值时发生的事情,它需要 隐含的 强制转换。
当比较字符串"99.99"
和数字99.99
时,大多数人同意它们是等价的。但是他们不完全相同,不是吗?它们是相同的值的两种不同表现形式,两个不同的 类型。你可以说它们是“宽松地等价”的,不是吗?
为了在这些常见情况下帮助你,JavaScript有时会启动 隐含的 强制转换来把值转换为匹配的类型。
所以如果你使用==
宽松等价操作符来进行"99.99" == 99.99
比较,JavaScript会将左手边的"99.99"
转换为它的number
等价物99.99
。所以比较就变成了99.99 == 99.99
,这当然是成立的。
虽然隐含强制转换是为了帮助你而设计,但是它也可能把你搞糊涂,如果你没有花时间去学习控制它行为的规则。大多数开发者从没有这么做,所以常见的感觉是隐含的强制转换是令人困惑的,并且会产生意外的bug危害程序,因此应当避免使用。有时它甚至被称为这种语言中的设计缺陷。
然而,隐含强制转换是一种 可以被学习 的机制,而且是一种 应当 被所有想要认真对待JavaScript编程的人学习的机制。一旦你学习了这些规则,它不仅是消除了困惑,而且它实际上是你的程序变得更好!这种努力是值得的。
注意: 关于强制转换的更多信息,参见本书第二章和本系列 类型与文法 的第四章。