数据类型

ECMAScript 有五种基本数据类型:undefinedNullBooleanNumberString,以及一种复杂的数据类型Object

typeof 操作符

首先注意typeof是一个操作符,不是一个函数,所以不是必须使用typeof()

typeof 会产生一些令人疑惑但技术上却正确的值:

typeof null // "object"

因为特殊值null被认为是一个空对象的引用

typeof undefined // "undefined"

Undefined 类型

变量在声明但未初始化时,这个变量的值就是undefined

但是用typeof对未声明与声明但未初始化的变量都将返回undefined

var a;
console.log(typeof a); // undefined
console.log(typeof b); // undefined

Null 类型

null类型表示一个空对象指针

所以定义的变量如果准备用于保存对象,那么最好将该变量初始化为null而不是其他值,这样一来只需要检查null就知道是否已经保存了对象的引用

实际上undefined是派生自null值,所以下面的值会返回为true

alert(null == undefined); //true

Boolean 类型

两种Boolean值: true, false (区分大小写)

Number 类型

八进制数第一位为必须是 0,如果后面的数值超出了范围,那么前导零将被忽略,后面的数字将被当做十进制解析

const a = 070;
console.log(a); // 56

const b = 08;
console.log(b); // 8

十六进制前两位必须是0x,进行算术运算时,都将转换成十进制数值

JavaScript 可以保存正零(+0)和负零(-0),被认为是相等

1. 浮点类型

由于保存浮点数所需内存空间为整数的两倍,所以如果小数点后没有跟任何数字,那么就会转换成整数来保存

极大极小的数值,可以使用e表示法

const a = 3.12e7; // 31200000
const b = 3e-17; //0.00000000000000003

浮点数的最高精度是 17 位,但是进行算数运算的时候精度远不如整数

0.1 + 0.2 != 0.3

if (a + b == 0.3) {
  alert('You got 0.3.');
} // 要避免这样比较

2. 数值范围

ECMAScript能够表示的最大最小数值Number.MAX_VALUENumber.MIN_VALUE

isFinite()函数的参数位于最小与最大数值之间会返回true

isFinite(Number.MAX_VALUE)也会返回true

0/0返回NaN,正数除以 0 返回Infinity,负数除以 0 返回-Infinity

3. NaN

NaN(Not a Number)是一个特殊的数值,用于表示一个本来要返回数值的操作数未返回数值的情况。NaN 有两个特点:

  • 任何涉及 NaN 的操作都会返回 NaN
  • NaN 与任何值都不相等,包括 NaN 本身 alert(NaN == NaN); // false

针对这个特点,我们可以使用isNaN()函数,该函数接收一个参数,会帮我们确定这个参数是否“不是数值”。它将参数尝试转换成数值,不能被转换成数值则返回true

console.log(isNaN(NaN)); // true
console.log(isNaN(true)); // false 可以转换成数字1
console.log(isNaN(1)); // false
console.log(isNaN('100')); // false 可以转换成数字10
console.log(isNaN('ok')); // true 不能转换成数值
console.log(isNaN('o')); // true 不能转换成数值

isNaN()也可用于Object

4. 数值转换

Number()parseInt()parseFloat()可以将非数值转换成数值

  • Number(): 会忽略前导 0;空字符串会返回 0;不包含任何有意义的数字值则返回NaN

  • parseInt(): 会忽略字符串前面的空格,直到找到第一个非空格的字符,如果第一个字符不是数字字符或者负号,则返回NaN

    能识别出各种整数格式(十进制,前导 0(仅在 ESMAScript 3 中),0x),这里列出几个比较特殊的输出:

    console.log(parseInt('hello')); // NaN
    console.log(parseInt('1234hello')); // 1234
    console.log(parseInt('')); // NaN
    console.log(parseInt('22.67')); // 22 小数点解析无效
    console.log(parseInt('070')); // esmascript 3中输出56, esmascript 5中输出70
    console.log(parseInt('80')); // 80
    console.log(parseInt('0xA')); // 10
    

    该函数可以接收第二个参数,用作转换时使用的基数:

    console.log(parseInt('A', 16)); // 10
    console.log(parseInt('A')); // NaN 没有基数,也没有0x开头
    

    所以建议任何情况下都明确指定基数

  • parseFloat(): 区别在于第一个小数点解析有效,第二个小数点开始无效,只用于解析十进制数字格式,始终会忽略前导零

    console.log(parseFloat('0xA')); // 0
    console.log(parseFloat('22.4.5')); // 22.4
    

String 类型

用单引号与双引号表示字符串完全相同。

字符串的特点:字符串不可变,修改字符串的过程就是生成新的,销毁旧的。如:

var str = 'js';
str = str + ' is good';
console.log(str); // js is good

转换成字符串:

  1. toString() : 该函数可以接收一个参数用于输出数值的基数,nullundefined没有这个方法

    var num = 10;
    console.log(num.toString(2)); // "1010"
    
  2. String(): 能够将任何类型转换成字符串,包括nullundefined;它的特点是如果值有toString()方法则调用该方法(无参数模式)并返回结果;如果null则返回null;如果是undefined则返回undefined

把某个值转换成字符串可以把它用'+'号与''连接在一起

Object 类型

后面面向对象章节详解

操作符

位操作符

对于有符号的整数,32 位中的前 31 位用于表示整数的值。第 32 位用于表示数值的符号:0 表示正 数,1 表示负数。这个表示符号的位叫做符号位

负数使用二进制补码的形式存储,计算补码的步骤:

  1. 求数值绝对值的二进制码
  2. 求二进制反码
  3. 得到的二进制反码加 1

1. 按位非(NOT)

var a = 30; // 0000 0000 0000 0000 0000 0000 0001 1110
var b = ~a; // 1111 1111 1111 1111 1111 1111 1110 0001
console.log(b); // -31

按位非的本质就是:操作数的负值减 1

2. 按位与(AND)、按位或(OR)

按位与操作符由一个和号字符(&)表示

3. 按位异或(XOR)

用符号(^)表示

4. 左移

左移操作符由两个小于号(<<)表示,这个操作符会将数值的所有位向左移动指定位数

var a = 27;
console.log(a.toString(2)); // 11011
var b = a << 6;
console.log(b.toString(2)); // 11011000000

左移不会影响操作数的符号位

5. 有符号右移

用(>>)表示

var a = 27;
console.log(a.toString(2)); // 11011
var b = a >> 4;
console.log(b.toString(2)); // 00001

在移位过程中,原数值中也会出现空位。只不过这次的空位出现在原数值的左侧、符号位的 右侧。而此时 ECMAScript 会用符号位的值来填充所有空位,以便得到一个完整的值。

var a = -27;
console.log(a.toString(2)); // 1111 1111 1111 1111 1111 1111 1110 0101
var b = a >> 4;
console.log(b.toString(2)); // 1111 1111 1111 1111 1111 1111 1111 1110
// 二进制:-10

image-20181029192404707

6. 无符号右移

用(>>>)表示

对于正数来说,无符号右移和有符号右移结果相同

对于负数来说情况大不相同,无符号右移是以 0 来填充空位,而不是像有符号右移那样以符号位的值来填充空位了;无符号右移操作符会把负数的二进制码当成正数的二进制码,由于原来负数是用二进制补码来表示的,所以最后得到的结果会非常大

var a = -27;
console.log(a.toString(2)); // 1111 1111 1111 1111 1111 1111 1110 0101
var b = a >>> 4;
console.log(b.toString(2)); // 0000 1111 1111 1111 1111 1111 1111 1110
console.log(b); // 268435454 直接表示成正数,故很大

比较操作符

易错规则:

  1. 两个都是字符串,比较对应的字符编码值
  2. 一个是数值,则将另一个操作数转换为一个数值,然后执行数值比较
  3. NaN 与任何操作数比较,都返回false

相等操作符

两组操作符:相等与不相等(先转换在比较)、全等与不全等(仅比较不转换)

1. 相等与不相等

用(==)或(!=)表示,这两个操作符都会先转换操作数,然后再比较相等性

几个特殊点:

  • null == undefined // true

  • "NaN"==NaN // false NaN与任何值判断是否相等都为false

  • true == 2 // false

  • null == 0 // false

    undefined == 0 // false

    比较相等性之前,null 与 undefined 不能转换成任何值。

2. 全等与不全等

与相等操作符区别就在于不转换数据类型就比较。

console.log('55' == 55); // true 将字符串转换成数值再比较
console.log('55' === 55); // false 字符串和数字不是同一类型 自然返回false
console.log(null === undefined); // false 这个和相等操作符的结果就不一样了,因为两者本身是不同类型

由于相等和不相等操作符存在类型转换问题,而为了保持代码中数据类型的完整性,我们推荐使用全等和不全等操作符

最后更新: 9/24/2019, 4:44:42 PM