One can use typeof
to determine whether a value is primitive or boxed.
Consider:
typeof "foo"; // "string"
typeof new String("foo"); // "object"
In combination with Object.prototype.toString
we could define the following two functions
var toString = Object.prototype.toString;
var is_primitive_string = function(s) {
return toString.call(s) === "[object String]" && typeof s === "string";
};
var is_boxed_string = function(s) {
return toString.call(s) === "[object String]" && typeof s === "object";
};
Are there any use cases for these two functions? (Or similar functions for Number
, Boolean
, etc).
The concept behind this question came from the following Comment by T.J.Crowder.
Should we ever care whether a value we have is primitive or boxed?
A boxed type means that the values are allocated in a block on the heap and referenced through a pointer.
Java boxingConverting from primitive types to object types is called boxing . Unboxing is the opposite operation. It is converting of object types back into primitive types.
I'd say there's virtually no point, you almost never care whether you're dealing with a string
primitive or a String
object.
There are edge cases. For instance, a String
object is an actual object, you can add properties to it. This lets you do things like this:
function test(arg) {
arg.foo = "bar";
}
If calling code passes in a string
primitive:
var s1 = "str";
test(s1);
...arg
gets promoted to a String
object and gets a property added to it, but that String
object isn't used by anything after test
returns.
In contrast, if calling code passes in a String
object:
var s2 = new String("str");
test(s2);
...then the property is added to that object and the calling code can see it. Consider (live copy):
var s1, s2;
s1 = "str";
display("[Before] typeof s1.foo = " + typeof s1.foo);
test(s1);
display("[After] typeof s1.foo = " + typeof s1.foo);
s2 = new String("str");
display("[Before] typeof s2.foo = " + typeof s2.foo);
test(s2);
display("[After] typeof s2.foo = " + typeof s2.foo);
function test(arg) {
arg.foo = "bar";
}
Output:
[Before] typeof s1.foo = undefined [After] typeof s1.foo = undefined [Before] typeof s2.foo = undefined [After] typeof s2.foo = string
Note that s2.foo
is a string, but s1.foo
isn't (because s1
was a string primitive, the object created when we promoted it in test
has nothing to do with the calling code).
Is there any use case for this? Dunno. I'd say it would be an extremely edgy edge case if so.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With