Does valueOf always override toString in javascript?

偶尔善良 提交于 2019-12-21 07:55:17

问题


Is there any expression where by an object's toString method is implicitly called overriding its valueOf method?

In the examples below, valueOf is always called implicitly (overriding toString).

"4" + {
    toString: function () {
        return "4";
    },
    valueOf: function () {
        return 6;
    }
};    // => "46", was expecting "44"

4 + {
    toString: function () {
        return "6";
    },
    valueOf: function () {
        return 4;
    }
};    // => 8

4 + {
    toString: function () {
        return 6;
    },
    valueOf: function() {
        return "4";
    }
};    // => "44"

i.e.:

Can we write an expression where by toString is implicitly called over valueOf (i.e without explicitly calling toString)?


回答1:


The + operator on Date objects uses toString not valueOf. Also if valueOf returns a non-primitive value then the toString method is called next. (JavaScript - The definitive guide, section 3.14) Using your example:

var result = "4" + {
    toString: function () {
        return "4";
    },
    valueOf: function () {
        return this; // returning an object, not a primitive
    }
};

Result is now 44.




回答2:


Is there any expression where by an object's toString method is implicitly called overriding its valueOf method?

Yes, that does happen whenever the abstract ToString operation is applied on an object, using the DefaultValue procedure with .toString() before .valueOf().

However, in your examples you have only used the addition operator which is like an exception from the standard behaviour. Since it does not only concatenate strings, but also sums numbers, it always uses valueOf on both operands before checking whether they're strings. See the note 1:

No hint is provided in the calls to ToPrimitive in steps 5 and 6. All native ECMAScript objects except Date objects handle the absence of a hint as if the hint Number were given; Date objects handle the absence of a hint as if the hint String were given. Host objects may handle the absence of a hint in some other manner.

So which operations do implicitly use the ToString instead of a hint-less ToPrimitive? Here are a few examples:

  • Everything about property names: The in operator, bracket notation, Object.getOwnPropertyDescriptor, Object.defineProperty, hasOwnProperty, …
  • Functions expecting strings as arguments: parseInt, parseFloat, encodeURI[Component], decodeURI[Component], [un]escape, Array::join, String::[last]indexOf, RegExp::exec
  • The Function constructor
  • The Array::sort algorithm's default compare function
  • The String constructor and String methods when casting the this object to a string
  • The RegExp constructor
  • The Error constructors
  • Lots of other functions not specified by EcmaScript but in the DOM or somewhere else, like alert, XMlHTTPRequest::open, querySelector, …



回答3:


Is there any expression

Yes. Here's an example that will use toString:

alert({
    toString: function () {
        return "4";
    },
    valueOf: function () {
        return 6;
    }
});  // alerts "4"


来源:https://stackoverflow.com/questions/20893187/does-valueof-always-override-tostring-in-javascript

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!