跳到主要内容

js高级 0.2 -> 操作运算符

· 阅读需 5 分钟

操作运算符,对象的特殊比较

前言

js高级程序设计(以下简称高程)这本书中提到的操作运算符,有些比较特殊的点,在以前的没有接触过,其中 对象这个比较有意思,也在面试题中出现。

toString() 与valueOf()

对象toString方法返回对象的字符串表示 即[object Object]

对象valueOf 返回对象的字符串,数值或布尔值,即对象本身

两者不同之处: 二者并存的情况下,在数值运算中,优先调用了valueOf,字符串运算中,优先调用了toString。

var test = {a:1 , b: 2}
console.log(test.toString(), test.valueOf()) // [object Object] {a: 1, b: 2}
test.valueOf = function () {return 10}
console.log(test.toString(), test.valueOf()) // [object Object] 10

加性操作符

  1. 如果有一个操作数是对象,数值或布尔值,调用toString(),取得字符串在相加

    var a = {}
    var b = a + 1
    // a 是一个对象 ,对象toString方法返回对象的字符串表示 即[object Object]
    console.log(b) // [object Object]1 相加后,有字符串,变成拼接

    上面第一点是高程说到的调用toString() 方法,但是下面改写了对象的valueOf,在运算时却是调用对象的valueOf拿到的值再去执行运算

     a.valueOf = function () {return 2}
    console.log(a.toString()) // [object Object]
    var b = a + 1
    console.log(b) // 3

    直接改写toString也是可以的

      a.toString = function () {return 2}
    console.log(a.toString()) // 2
    var b = a + 1
    console.log(b) // 3

    同时改写呢

      a.toString = function () {return 2}
    a.valueOf = function() {return 10}
    var b = a + 1
    console.log(b) // 11

    这个结果说明了,valueOf 比toString的优先级高

  2. 对于undefined 和null

      var c = undefined, d = null
    var z
    b = c + 1
    z = d + 1
    console.log(b, z) // NaN 1

减法操作符

  1. 如果有一个操作数是对象,则调用对象的valueOf 得到对象的数值,如果对象没有valueOf方法,则调用toString()方法

      var sa = {}
    console.log(sa.valueOf()) // {}
    var sb = 3 - sa
    console.log(sb) // NaN
    sa.valueOf = function () {return 1}
    var testb = 3 - sa
    console.log(testb) // 2

关系操作符 如 < > <=, >=

  1. 有一个操作数是对象的,跟上同理, 都是调用对象的valueOf 得到对象的数值,如果对象没有valueOf方法,则调用toString()方法

相等操作符 ==

  1. 有点不同,只有一个操作数是对象时,调用对象的valueOf 得到对象的数值,如果对象没有valueOf方法,则调用toString()方法然后进行比较

      var qa = {}
    console.log(qa == 1) // false
    qa.toString = function () {return 1}
    console.log(qa == 1); // true
    qa.valueOf = function () {return 2}
    console.log(qa == 1); // false

    两个都是对象比较

    如果两个操作数都是对象,则对比两个对象是不是同一个对象,如果两个对象都指向同一个对象返回true

      var a1 = {a: 2, b: 1}
    var b1 = a1 // 或者b1 = new Object(a1)
    console.log(a1 == b1) // true
    var b2 = {a: 2}
    console.log(a1 == b2) // false

面试题

之前面试遇到的一个题目,挺有意思的

  var a = ?;
if (a == 1 && a == 2 && a == 3) {
console.log(a)
} else {
console.log('不成立')
}

意思是要让if条件成立,那么a的值是多少,有了上面的知识,其实这道就非常简单了

答案

  var ta = {valueOf: function () { return ++this.b}, b: 0}
if (ta == 1 && ta == 2 && ta == 3) {
console.log(ta) // {valueOf: ƒ, b: 3}
} else {
console.log('不成立')
}
// 只要每次比较都不断去刷新对象的valueOf的值即可