JavaScript基础知识-基本概念
typeof操作符
typeof 操作符返回一个字符串,表示未经计算的操作数的类型。
// 数值 typeof 37 === 'number'; typeof 3.14 === 'number'; typeof(42) === 'number'; typeof Math.LN2 === 'number'; typeof Infinity === 'number'; typeof NaN === 'number'; // 尽管它是 "Not-A-Number" (非数值) 的缩写 typeof Number(1) === 'number'; // Number 会尝试把参数解析成数值 typeof 42n === 'bigint'; // 字符串 typeof '' === 'string'; typeof 'bla' === 'string'; typeof `template literal` === 'string'; typeof '1' === 'string'; // 注意内容为数字的字符串仍是字符串 typeof (typeof 1) === 'string'; // typeof 总是返回一个字符串 typeof String(1) === 'string'; // String 将任意值转换为字符串,比 toString 更安全 // 布尔值 typeof true === 'boolean'; typeof false === 'boolean'; typeof Boolean(1) === 'boolean'; // Boolean() 会基于参数是真值还是虚值进行转换 typeof !!(1) === 'boolean'; // 两次调用 ! (逻辑非) 操作符相当于 Boolean() // Symbols typeof Symbol() === 'symbol'; typeof Symbol('foo') === 'symbol'; typeof Symbol.iterator === 'symbol'; // Undefined typeof undefined === 'undefined'; typeof declaredButUndefinedVariable === 'undefined'; typeof undeclaredVariable === 'undefined'; // 对象 typeof {a: 1} === 'object'; // 使用 Array.isArray 或者 Object.prototype.toString.call // 区分数组和普通对象 typeof [1, 2, 4] === 'object'; typeof new Date() === 'object'; typeof /regex/ === 'object'; // 历史结果请参阅正则表达式部分 // 下面的例子令人迷惑,非常危险,没有用处。避免使用它们。 typeof new Boolean(true) === 'object'; typeof new Number(1) === 'object'; typeof new String('abc') === 'object'; // 函数 typeof function() {} === 'function'; typeof class C {} === 'function' typeof Math.sin === 'function';
在JavaScript最初的实现中,JavaScript中的值是由一个表示类型的标签和实际数据值表示的。对象的类型标签是0。由于null代表的是空指针(大多数平台下值为 0x00),因此,null的类型标签是0,typeof null也因此返回 "object"。
在 ECMAScript 2015 之前,typeof 总能保证对任何所给的操作数返回一个字符串。即便是没有声明的标识符,typeof 也能返回 'undefined'。使用 typeof 永远不会抛出错误。
但在加入了块级作用域的 let 和 const 之后,在其被声明之前对块中的 let 和 const 变量使用 typeof 会抛出一个 ReferenceError。块作用域变量在块的头部处于“暂存死区”,直至其被初始化,在这期间,访问变量将会引发错误
Undefined类型
Undefined类型只有一个值,即undefined。在使用var声明变量但未对其加以初始化时,这个变量的值就是undefined。
null类型
Null类型也是只有一个值:null。位于null和undefined之间的相等操作符(==)总是返回true。
在保存对象的变量还没有真正保存对象,就应该明确地让该变量保存null值。这样做不仅可以体现null作为空对象指针的惯例,而且有助于进一步区分null和undefined。
Boolean类型
该类型只有两个值:true和false
数据类型 | 转换为true的值 | 转换为false的值 |
---|---|---|
Boolean | true | false |
String | 任何非空字符串 | ""(空字符串) |
Number | 任何非零字符串 | 0和NaN |
Undefined | undefined | |
Object | 任何对象 | null |
Number类型
该类型使用IEEE754格式表示整数和浮点数值。 浮点数值:数值中必须包含一位小数点,并且小数点后面必须至少有一位数字。
保存浮点数值需要的内存空间是保存整数值的两倍,因此ECMAScript会不失时机地将浮点数值转换为整数值。显然,如果小数点后面没有跟任何数字,那么这个数值就可以作为整数值来保存。同样地,如果浮点数值本身表示就是一个整数(1.0),那么该值也会被转换为整数。
1、数值范围
由于内存的限制,ECMAScript并不能保存世界上所有的数值。ECMAScript能够表示的最小数值保存在Number.MIN_VALUE中--大多数浏览器,这个值是5e-324;能够表示的最大数值保存在Number.MAX_VALUE中--大多数浏览器,这个值是1.797....e+308。如果超出了就被自动转换为Infinity值。
使用isFinite()来检测是否为Infinity
2、NaN
即非数值,这个数值用于表示一个本来要返回数值的操作数未返回数值的情况。任何数值除以0都会返回NaN。NaN与任何值比较都不相等,包括NaN本身。
使用isNaN()函数来检测某个值是否为NaN
3、数值转换
1、Number()-可以用于任何数据类型
- 如果是Boolean值,true和false将分别被转换为1和0.
- 如果是数字,只是简单的传入与返回。
- 如果是null,返回0。
- 如果是undefined,返回NaN。
- 如果是字符串,遵循下列规则:
如果字符串中只包含数字,则将其转为了十进制数值;
如果字符串中包含有效的浮点格式,则将其转换为对应的浮点数值;
如果字符串中包含有效的十六进制格式数字,则将其转换为相同大小的十进制整数;
如果字符串是空的,则将其转换为0;
如果字符串中包含上述格式之外的值,则将其转为NaN。 - 如果是对象,则调用对象的valueof()方法,然后依照上述规则进行转换。如果转换的结果是NaN,则调用对象的toString()方法,然后再次根据上述规则进行转换返回的字符串。
2、parseInt()
- 忽略字符串前面的空格,直至找到第一个非空格字符。
- 如果第一个字符不是数字或者负号,返回NaN
- 空字符转换为NaN。
- 如果第一个字符是数字,则继续解析下面字符,直到完成所有字符的解析或者遇到了一个非数字字符。
- 函数提供第二个参数:转换时使用的基数(多少进制)
3、parseFloat()
- 与parseInt()函数类似,从一个字符开始解析每个字符,一直解析到字符串的末尾或者遇见一个无效的浮点数字符为止。
String类型
String类型用于表示由零或多个16位Unicode字符组成的字符序列,即字符串。可以由双引号或者单引号表示。
1、字符串特点
ECMAScript中的字符串是不可变的,也就是说,字符串一旦创建,它们的值就不能改变。要改变原来保存的值,首先要销毁原来的字符串,然后在用另一个新值填充该变量。
2、转换为字符串
- toString():数值,布尔值、对象和字符串值都有一个toString()方法。但null和undefined没有这个方法。
多数情况下,不需要传入参数。但是,在调用数值的toString()方法时,可以传递一个参数:输出数值的基数。 - 在不知道要转换的值是不是null或undefined的情况下,还可以使用转型函数String(),这个函数能够将任何类型的值转换为字符串。
- String()函数遵循下列转换规则:
如果值有toString(),则调用该方法并返回相应的结果。
如果值是null,返回'null',
如果是undefined,返回'undefined'
Object类型
ECMAString中的对象其实就是一组数据和功能的集合。对象可以通过执行new操作符后跟要创建的对象类型的名称来创建。
Object的每个实例都具有下列的属性和方法:
- constructor:保存着用于创建当前对象的函数。
- hasOwnProperty(propertyName):用于检查给定的属性在当前对象实例中是否存在。
- isPrototypeOf(Object):用于检查传入的对象是否为传入对象的原型。
- propertyIsEnumerable(propertyName):用于检查给定的属性是否能够使用for-in语句来枚举。
- toLocaleString():返回对象的字符串表示,该字符串与执行环境的地区对应。
- toString():返回的对象的字符串表示
- valueOf():返回对象的字符串、数值或布尔值表示。
位操作符
位操作符用于在最基本的层面上,即按内存中表示数值的位来操作数值。ECMAScript中的所有数值以IEEE-754 64位格式存储,但位操作符并不直接操作64位的值。而是将64位的值转换为32位整数,然后执行操作,最后将结果转换为64位。
对于有有符号整数,前31位用于表示整数的值。第32位用于表示数值的符号:0表示整数,1表示负数。这个表示符号的位叫做符号位,符号位的值决定了其他位数值的格式。其中,正数以纯二进制格式存储,31位中的每一位都表示2的幂。
负数同样以二进制码存储,但使用的格式是二进制补码。计算一个数值的二进制补码,需要经过下列3个步骤:
- 求这个数值绝对值的二进制码
- 求二进制反码,即将0转换为1,1转换为0;
- 得到二进制反码加1。
有一个严重的副作用,即对于特殊的NaN和Infinity值应用位操作时,这两个值都会被当成0来处理。
对于非数值应用位操作符,会先使用Number()函数将该值转换位一个数值,然后应用位操作符。
1、按位非(NOT)
由一个波浪线(~)表示,执行按位非的结果就是返回数值的反码。 本质是操作数的负值减1。
var num1 = 25 // 00000000000000000000000000011001
var num2 = ~num1 // 11111111111111111111111111100110
2、按位与(AND)
由一个和号字符(&)表示,它有两个操作数。从本质上讲,按位与操作就是将两个数值的每一位对齐,然后根据下表中的规则,对相同位置上的两个数执行AND操作。
按位与操作只在两个数值的对应位都是1时才返回1,任何一位是0,结果是0.
3、按位或(or) 由一个竖线(|)表示,同样也有两个操作数。按位或操作在有一个位是1的情况下就返回1,而只有在两个位都是0的情况下才返回0.
4、按位异或(XOR) 由一个插入符号(^)表示。按位异或与按位或的不同之处在于,这个操作在两个数值对应位上只有一个1时才返回1,如果对应两位都是1或都是0,返回0。
5、左移
由两个小于号(<<)表示,这个操作符会将数值的所有位向坐移动指定的位数。例如将数值2(二进制码为10)向左移动5位,结果就是64(二进制码为1000000)
6、有符号右移
由两个大于号(>>)表示,这个操作符会将数值向右移动,但保留符号位(即正负号)。有符号右移与左移操作恰好相反。
7、无符号右移
由三个大于号(>>>)表示,这个操作符会将数值的所有32位向右移动。对正数来说,无符号右移的结果与有符号右移的结果相同。
布尔操作符
1、逻辑非
由一个叹号(!)表示。可以用于ECMAScript任何值。都会返回一个布尔值。遵循下列规则:
- 如果操作数是一个对象,返回false;
- 如果操作数是一个空字符串。返回true;
- 如果操作数是一个非空字符串,返回false;
- 如果操作数是数值0,返回true;
- 如果操作数是任意非0数值(包括Infinity),返回false;
- 如果操作数是null,返回true。
- 如果操作数是NaN,返回true。
- 如果操作数是undefined,返回true。
同时使用两个逻辑非操作符,实际上就会模拟Boolean()转型函数的行为。其中,第一个逻辑非操作会基于无论什么操作数返回一个布尔值,而第二个逻辑非操作则对该布尔值求反。
2、逻辑与
由两个和号(&&)表示。
- 如果第一个操作数是对象,则返回第二个操作数。
- 如果第二个操作数是对象,则只有在第一个操作数的求值结果位true的情况下才会返回该对象。
- 如果两个操作数是对象,则返回第二个操作数。
- 如果有一个操作数是null,则返回null。
- 如果有一个操作数是NaN,则返回NaN。
- 如果有一个操作数是undefined,则返回undefined。
3、逻辑或
由两个竖线(||)表示。
- 如果第一个操作数是对象,则返回第一个操作数;
- 如果第一个操作数求值结果为false,则返回第二个操作数;
- 如果两个操作数是对象,则返回第一个操作数;
- 如果两个操作数是null,则返回第一个操作数;
- 如果两个操作数是NaN,则返回NaN;
- 如果两个操作数是Undefined,则返回undefined。
4、==
- 如果有一个操作数是布尔值,则在比较前先将其转换为数值--false转换为0,而true转换为1.
- 如果有一个操作数是字符串,另一个操作数是数值,在比较前将字符串转换为数值。
- 如果有一个操作数是对象,另一个操作数不是,则调用对象的valueof()方法,用得到的基本类型值按照前面的规则进行比较。
- null和undefined是相等的。
- 不能将null和undefined转换为其他任何值。
- 如果有一个操作数是NaN,则返回false。
函数
1、理解参数
ECMAScript函数的参数与大多数其他语言中函数的参数有所不同。ECMAScript函数不介意传递进来多少个参数,也不在乎传进来参数是什么数据类型。原因是ECMAScript中的参数在内部是用一个数组来表示的。函数接收到的始终都是这个数组。这是事实说明了ECMAScript函数的一个重要特点:命名的参数只提供便利,但不是必需的。
2、没有重载
ECMAScript函数不能像传统意义上那样实现重载。而Java中,可以为一个函数便携两个定义,只要这两个定义的签名(接收的参数的类型和数量)不同即可。ECMAScript函数没有签名,因为其参数是由包含零或者多个值的数组来表示的。
作者: zhangwinwin
链接: 基本概念
来源: github