美文网首页
《你所不知道的JavaScript》-值与类型

《你所不知道的JavaScript》-值与类型

作者: 浩神 | 来源:发表于2018-08-26 15:16 被阅读10次

    变量没有类型,值才有。变量可以随时持有任何类型的值。

    所有的值都有一个类型,可能是:

    • Undefined

    • null

    • Number

    • String

    • Boolean

    • Object

    • Symbol

      除对象外,其他统称为基本类型,我们可以使用typeof来获取一个值的类型,但null比较特殊。

      typeof null === 'object' // true
      

      这是一个由来已久的bug,我们需要使用符合条件检测null。

      var a = null;
      (!a && typeof a === 'object'); // true
      

    另外一个比较特殊的是函数。

    var a = () => {}
    typeof a; // function
    

    查阅规范就会知道,function是object的一个“子类型”。具体而言,函数是“可调用对象”,他有一个内部属性[[Call]],该属性使其可以被调用。

    null和undefined

    Undefined

    变量在未持有值的时候为undefined。大多数开发者倾向于将undefined等同于undeclared(未申明),但在JavaScript中完全是两回事情。

    已在作用域中声明但还没有赋值的变量是undefined,相反,还没有在作用域中声明过得变量是undeclared。

    var a;
    a; // undefined
    b; // ReferenceError: b is not defined
    

    对UNdeclared的变量执行typeof,会得到undefined,这让人抓狂,因为typeof有一个特殊的安全防范机制。这种处理使得我们比较容易判断当前环境是否已经引入了某一变量。

    if(typeof abc === 'undefined') {
        abc = function() {
            // do some thing
        }
    }
    

    判断a是否已经在当前环境中,使用typeof a === 'undefined', 而不是 if(a)

    Null还是Undefined

    • null指的是空值(empty value)
    • undefined指的是没有值(missing value),从未赋值过

    void 0

    鉴于在非严格模式下,我们可以为全局标识符undefined赋值。可以看到一些人这样写代码:

    var a = void 0 
    

    表达式void没有返回值,它获得一个纯粹的undefined。void并不改变表达式的结果,只是让表达式不返回值。

    数组

    1. 在JavaScript中,数组可以容纳任何类型的值
    2. 对数组声明之后即可向其加入值,不需要预设大小。
    3. 使用delete运算符可以将单元从数组中删除,但是单元删除之后,数组的length属性并不会发生变化。
    4. 数据通过数字进行索引,但有趣的是数组也是对象,所以也可以给它添加字符串键值。但这些不计算在数组长度之内。

    类数组转换为数组

    例如一些DOM查询返回的DOM元素列表,或者函数的arguments对象可以通过以下方法转换为数组:

    • concat()
    • forEach()
    • indexOf()
    • slice()
    • Array.from

    字符串

    字符串是不可变的,意味着对字符串的操作往往不会直接去修改已有字符串,而是生成新的字符串。

    数字

    JavaScript只有一种数值类型:number。JavaScript的数字根据IEEE 754标准实现的。

    二进制浮点数最大的问题(所有遵循IEEE 754规范的语言),会出现如下情况:

    0.1 + 0.2 === 0.3 // false
    

    以上情况的原因在于二进制浮点数中的0.1和0.2并不是十分精确,它们相加的结果比较接近0.300000000000004,所以判断结果是false。

    为了解决上面的问题,最常见的方法是设置一个误差范围值,通常为“机器精度(machine epsilon)”, 对于JavaScript的数字而言,这个值通常是 2^-52。从ES6开始这个值定义在 Number.EPSILON中。所以判断小数是否相等可以这样写:

    Math.abs(n1 - n2) < Number.EPSILON;
    

    检测一个数字是否是整数,可以使用:

    Number.isInteger(33); // true
    Number.isInteger(33.00); // true
    Number.isInteger(42.3) // false
    

    不是数字的数字

    NaN意指“不是一个数字”,将她理解为“无效的数值”可能更准确。例如:

    var a = 2 / 'foo';
    typeof a === 'number'; // true
    

    NaN是一个“禁戒值”, 用于指出数字类型中的错误情况,即“执行数学运算没有成功”。

    检测NaN

    NaN是唯一一个不和自身相等的值(非自反, reflexive,即 x === x 不成立)。

    1. 不要使用内建的全局工具函数 isNaN
    window.isNaN(NaN) // true
    window.isNaN('foo') // true
    

    很明显'foo'不是NaN。

    1. ES6提供了一个工具函数: Number.isNaN().
    Number.isNaN(NaN) // true
    Number.isNaN('foo') // false
    
    1. 利用NaN不等于自身这一点,可以使用:

      if(!Number.isNaN) {
          Number.isNaN = n => n !== n;
      }
      

    如果你仍在代码里使用window.isNaN, 迟早会出现bug

    相关文章

      网友评论

          本文标题:《你所不知道的JavaScript》-值与类型

          本文链接:https://www.haomeiwen.com/subject/exaniftx.html