数据类型转换、运算符、表达式

161 阅读7分钟

数据类型转换、运算符、表达式

1. 数据类型转换

  1. 定义: 将不需要的数据类型, 转化为需要的数据类型

  2. JS 四大特点之一:

    • 弱类型( 由数据类型来决定数据 ): 3 大特点
      1. 声明变量时, 不需要提前指定变量的数据类型
      2. 同一个变量先后可保存不同类型的数据
      3. 不同数据类型间可相互转化
    • typeof 函数的使用
      • 作用: 获取指定数据的数据类型
      • 语法: typeof(变量) 或者 typeof 变量
      • Ex: var result = typeof(变量)
  3. 何时: 只要给定的数据类型不是想要的

  4. 如何: 2 种

    1. 隐式转换: 不需要程序员干预, 由 JS 自动完成的数据类型转换

      • 何时: 只要给定的数据类型和 JS 程序需要的类型不相符, JS 就会根据自己的需要, 自动转化数据类型
        • 默认: 一切都转为 number 类型, 再做计算
          • 为什么: 因为 number 类型最适合计算
          • Boolean: true -> 1 false -> 0
        • 特殊: + 运算中, 只要碰到一个字符串 -> 一切都转为字符串, + 运算变为字符串拼接
    2. 强制转换: 程序员主动调用函数完成的数据类型转换

      • 何时: 只要给定的数据类型不是想要的, 且自动转换的结果也不是想要的, 就要强制转换

        1. 其他类型转 number: 2种

          1. Number(x): 将 x 转为 number 类型

            • 何时: 都是隐式转换, 其实相当于自动调用 Number(x), 很少主动使用
            • 问题: 只能转换纯数字组成的字符串和 Boolean 类型
            • 特例: 1. Number() -> 0 2. Number('') -> 0 3. Number([]) -> 0 4. Number(null) -> 0 5. Number(undefined) -> NaN 6. ``Number({}) -> NaN`
            • 如果转不了: 就返回 NaN
              • NaN: 不是一个数字的任何值 -> Not a Number
                • NaN 参与任何运算结果只能是 NaN
          2. parseFloat(str) / parseInt(str): 将 string 转为 number 类型, 自动去除末尾非数字字符

            • parseFloat() 可保留小数部分

            • ParseInt()去掉小数部分

            • 何时: 只要将字符串转 number, 首选 parseFloat

              • 如果确实需要去掉小数, 才选 parseInt
              • 如果转不了, 也返回 NaN
            • 强调: 参数应该是string类型

              • 如果给定的值不是 string 类型, 则先执行隐式转换, 转为 string 类型, 再转 number
              • Ex: parseFloat(true) -> parseFloat("true") -> NaN
        2. 其他类型转 string: 2种

          1. x.toString(): 将 x 转为字符串类型
            • x 不能是 nullundefined, 会报错 -> toString() 不是万能的
          2. String(x): 将 x 转为字符串类型 -> 万能
            • 其实, 隐式转为 string 时, 都是自动调用 String()
        3. 其他类型转 Boolean 类型: 1种

          • Boolean(x):

            • 规则: 只有 5 个值会被转为 false: 0, "", NaN, null, undefined
              • 其余都转为true
          • 其实, 隐式转为 Boolean 时, 都是自动调用 Boolean(x)

        • 注意: 1. 凡是从页面上获得的一切都是字符串类型

          1. typeof 变量: 可输出变量中值的数据类型名

2. 运算符和表达式

  • 程序: 人的想法在计算机中的执行

  • 运算符: 程序中模拟人的想法的特殊符号

  • 表达式: 由数据, 变量和运算符组成的完成一项单一任务的语句

2.1 算数运算:

+, - , * , /, %

  1. %: 模运算 / 取余数 -> 被除数/除数 ,不要商, 要除不尽的余数部分
    • 何时: 1. 取余数 2. 判断能否整除
      • 判断偶数: 能被 2 整除 -> n%2 == 0
      • 判断奇数: 不能被 2 整除 -> n%2 != 0
  2. 隐式转换: 默认都转 number
    • 特殊: + 运算中, 碰到字符串, 都转字符串, + 运算变为字符串拼接
  3. 舍入误差: 计算机中, 也有计算不尽的数值
    • 解决:
      1. 按指定位数四舍五入: n.toFixed(2) -> 会变成字符串
        • 今后几乎所有显示钱数的地方都要 toFixed(value)
      2. 存储: 保存很长位数的小数: 0.39999999
2.2. 关系运算:

用两个值做比较, 做判断

  • 包括: >, <, >=, <=, ==, !=, ===, !==
  1. 返回值: Boolean
  2. 隐式转换: 默认都转 number
    • 特殊: 1. 两个值都是字符串, 则不再转数字, 而是依次比较每个字符的 unicode 号 2. 判断 NaN:
      • NaN 和任何值做>, <, >=, <=, == 5 种比较时, 永远 false
      • NaN 和任何值做 !=比较时, 永远是 true
      • 问题: Boolean(NaN == NaN) -> false: 用普通的 == 无法判断 NaN
        • 解决: isNaN(num) 专门代替 ==, 用来判断 number是不是 NaN
          • 何时: 只要判断是不是 NaN, 都用 isNaN(number)
          • 反用: 判断一个值是不是数字: !isNaN(number)
      1. 区分 nullundefined
        • 问题:==比较时, 会自动将 undefined 隐式转为 null
          • Boolean(null==undefined) -> null=null -> ture
        • 解决: ===: 全等 -> 类型必须先相同, 值再相等
          • 其实 === 就是不带隐式转换的 ==
  3. 补充: JS 中除数可以为0, 结果为 infinite( 无穷 ) -> finite: 有限
    • infinite 可参与关系运算, isFinite(num) 专门判断一个数字是否在有效范围内
      • numer 在有效范围内返回 true, 超出最大数字范围为 false
      • Ex: isFinite(undefined) -> false, isFinite(NaN) -> false, isFinite(null) -> ture
2.3. 逻辑运算

将多个关系运算, 综合起来得到最终结论

  • 何时: 只要根据多个条件, 综合得出最终结论时
  • 包括: && -> 与, || -> 或 , ! -> 非
  1. 条件1 && 条件2...:
    • 要求所有条件都为 true, 结果为 true
    • 只要一个条件为 false, 结果为 false
  2. 条件1 || 条件2...:
    • 只要一个条件为true, 结果为 true
    • 除非所有条件都为false, 结果才为 false
  3. ! 条件: 颠倒条件的判断结果
  4. 隐式转换: 默认将每个条件都转为 Boolean 类型
    • 在逻辑运算中都自动转为布尔类型进行运算, 由 truefalse 来看要不要进一步判断, 逻辑运算的返回值不一定是布尔值
    • 在利用短路逻辑时候, 不再返回布尔值, 若参与运算的都是值, 将在两个值之间选择一个返回
    • 短路逻辑: 如果前一个条件已经可以得出最终结论, 则后续条件不再执行
      • &&: 只有前一个条件为 false 时, 后续条件才不执行
      • ||: 只要前一个条件为 true 时, 后续条件不再执行
    • 利用短路逻辑:
      1. 简单分支结构: 1个条件, 1件事, 只有满足才做
        • 如何: 条件 && ( 操作 )
          • 若是 && 后面是赋值的运算, 最好加上括号, 因为赋值的等号的优先级特别低
          • 练习中 -> 运算符优先级: 优先级高的运算, 先计算 -> 改变优先级: 用 ()
      2. 实现默认值 / 备用值:
        • 如何: 值1 || 值2
          • 如果值1可以被转为true, 就选择值1使用
          • 如果值1不能转为 true, 就选择值2使用
2.4. 位运算:
  1. &: 按位与, 将两边的操作数转换成二进制, 每位的数字, 只有对应都为 1 的时候, 该位的结果才为 1, 否则该位的结果就是 0

    • Ex: 5 & 3

      5: 101

      3: 011

      ---------------

      &: 001

    • 作用: 判断一个数字的奇偶性 -> 判断的数字与 1 做按位与

      • Ex: 5 & 1 5: 101 1: 001 ----------- &: 001 -> 1 奇数
  2. |: 按位或, 两边的操作数转换成二进制, 比较每位上的数字, 两个数中只要有 1 个是 1 的话, 该位的结果为1, 当两个数字为 0 时, 值为 0

    • 场合: 向下取整
    • Ex: 5 | 3 5: 101 3: 011 ---------- |: 111
  3. 左移 << / 右移 >>:

    • <<: 左移 按位左移, 将 2 进制数向左移动几位, 后面以 0 补齐

      • Ex: 1<<3: 1 左移 3 位 -> 相当于 1* 2 的 3 次方 -> 8

        2<<3: 等于 2* 2的3次方 -> 16

    • >>: 按位右移, 将 2 进制数向右移动几位, 前面补0 Ex: 8>>3: 8 右移 3 位 -> 1

  4. 下取整:

    • n ^ 0 , n | 0, n >>> 0 -> 代替 / 简化 Math.floor(n)
  5. 交换两变量的值:

    • var a=3, b=5;
    • 方法一: var t=b; b=a; a=t;
    • 方法二: a+=b; b=a-b; a=a-b;
    • 方法三: a^=b; b^=a; a^=b;
    • 方法四:a=[b,b=a][0];
2.5. 赋值运算
  • 扩展赋值运算: 对特殊赋值运算的简写
    • a=a+b: 将 a + b 的值, 存回 a 中 -> 将 b 的值累加到 a 上
    • 可简写为 a += b;
    • a = a - b; -> a -= b;
    • a = a * b; -> a *= b;
    • a = a / b; -> a /= b;
    • a = a % b; -> a %= b;
    • 更简化: 递增递减运算 -> 如果每次累加 1 / 累减 1
      • a += 1 -> a++
      • a -= 1 -> a--
2.6. 三目运算符

需要三个操作数 / 表达式

  • 语法: 表达式 1 ? 表达式 2 : 表达式 3
    • 表达式 1 的运行结果应为 Boolean 类型
      • 若表达式 1 为 true, 则整个表达式的值为表达式 2 的运算结果
      • 若表达式 1 为 false, 则整个表达式的值为表达式 3 的运算结果
2.7. 前 ++ 和后 ++
  • 如果单独使用, 前后都一样
  • 如果参与到其他表达式中时:
    • 相同: 变量中的值一定都会 + 1
    • 不同: ++i, 返回 + 1 后的
      • i++, 返回未 + 1 的

提示: 所有表达式都是从左向右依次执行

  • 如果前一个表达式修改了变量的值, 则会影响后续表达式的执行