|Written by Ian Elliot|
|Monday, 25 June 2018|
Page 2 of 3
To make sure you have all of this worked out, see if you can answer the following questions:
1. What is
2. What is
3. What is
4. What is the final value of a
5. What is the final value of a
Try to work them out without typing in the code, then see if you are right by running the code.
Even if you are right, see below for the full explanations.
Every Object Has a String Value
Just as the valueOf method gives every object a value, the toString method does the same sort of thing for strings.
Now we have a custom object which has a value and a String representation.
As in the case of valueOf, you don't have to return a String object as the result of a toString method, but not to do so would be misleading in the extreme.
So when is toString used in an expression?
There are two ways that toString can be invoked during the evaluation of an expression.
The first is to get a primitive value for the object.
Put simply, if the expression evaluator fails to get a primitive object from valueOf it will try toString to get one.
That is, it first uses the valueOf method. If this returns a primitive value then it stops. If this returns a general object the evaluator next tries the toString method to see if this can provide a primitive value. If this works the value is used in the expression; if it doesn't then you get a runtime error:
To see this in action try:
Notice that in this case both methods return an empty object, which isn't a primitive value.
Notice that toString can return a Number object and this will work:
This doesn't throw a runtime error and it results in 2 stored in a.
The evaluator doesn't care about what type of primitive object it gets from valueOf or toString – as long as it is a primitive object.
The second way the toString method can be called is if the primitive value obtained earlier is the wrong sort of primitive.
For example, consider concatenation. You might think that if one of the operands in the expression was a String:
then the toString method would be called to convert the other object to a String.
This isn't what happens.
What happens is the same two steps – first valueOf is called and if it doesn't provide a primitive value toString is called.
At this point we assume we have a primitive value, pv, ready to be used in the expression.
If the expression turns out to be concatenation, because of the other operand being a String, then the toString method is called on the primitive value, i.e. pv.toString() is used in the expression. The original object's toString method isn't used.
This is because the object's value is more important than its String representation.
is "11" because valueOf returns 1 which is a primitive value and then 1.toString() is called to give "1" which is used in the concatenation. Object1's toString method doesn't get used.
Also notice that it doesn't matter which of the two methods returns the primitive value.
The same sort of thing happens if your custom object returns a String primitive value when the expression needs a Number. In this case the primitive value's valueOf is called in an attempt to obtain a Number primitive.
If this doesn't work the result of the expression is NaN – Not A Number.
Putting all this together:
Built-In Objects and Type Conversion
Built-in objects like String have a predefined valueOf method that returns sensible values for the object.
What is a sensible value for a String?
The obvious answer is a String.
What is the sensible value for a Number?
The obvious answer is a Number.
So far so good.
In both cases valueOf returns the same primitive type as the original object. In a sense a Number and a String are their own object values.
What happens if a Number is involved in an expression that requires a String?
The answer is that its toString method is called.
What happens if a Number is involved in an expression that requires a string?
In this case the internal toNumber method is called. You can't make use of the toNumber method but it is automatically called to convert a String to a Number when required.
Consider, for example:
In this case when the String object is used in the expression a*num then its default valueOf method is called automatically and it returns a primitive string. Next, internally, the toNumber function is called to convert the value of this string to a number. If the string cannot be converted then the result is NaN – Not a Number.
|Last Updated ( Monday, 25 June 2018 )|