Why in Javascript, 7 (a number) is not an instance of Number?

Asked

Viewed 181 times

11

When we do the following test below, it is returned false.

console.log(7 instanceof Number); // FALSE

However, in the second test, it is returned true.

var number = new Number('3');

console.log(number instanceof Number) // TRUE

In a second scenario, we also have a variation when we use typeof:

typeof 1 // "number"

typeof new Number(1) // "object"

I do not understand why this, since, in the examples below, both the object like the number shall have the method established in Number through the prototype!

Behold:

Number.prototype.square = function ()
{
   return Math.pow(this, 2);
}

var x = 3;

x.square(); // 9

new Number(3).square() // 9

(3).square() // 9

Does anyone know why this happens craziness variation?

  • Perhaps because 7(or any other number) is treated as a string when it is not declared?

  • 1

    Sorry now I understood better, I will finish the answer and already put

  • 1

    @Marcelobonifazio, typeof 7 = 'number'. typeof '7' = 'string'

  • It is not only 7 that is not an instance of Number.. Its title is still half way misleading

  • 1

    When someone gives a -1, could you at least explain , to see what I can improve on my question

  • 1

    need to explicitly instantiate...

  • @Wallacemaxters I took -2 and no one explained it to me either, but the day I’m going through today... what least worries me is the negatives here

Show 2 more comments

3 answers

15


In Javascript, there are primitive types for String, Number and Boolean (besides Object and of the types Null and Undefined, which only have one instance each). So, primitive values like the ones in the example below are not objects:

var texto = "Texto";
var numero = 7;
var booleano = true;

texto instanceof String;     // false
numero instanceof Number;    // false
booleano instanceof Boolean; // false

The operator instanceof does not say the type of value. If the value is an object, the instanceof says if what’s on the right side is one of the prototype chain of this object - and so new Number(7) instanceof Number === true, since the number was created with the constructor Number.

What gives the type of value is the operator typeof, with which you get the kind of primitives:

typeof texto;     // "string"
typeof numero;    // "number"
typeof booleano;  // "boolean"

When you try to access a property, the engine knows how "wrap" the value in an object of the corresponding type (String, Number or Boolean), to then return the property. This is similar to autoboxing java. The created object is temporary, it does not exist as a variable after obtaining the value of the property (although Engines can perform optimizations and keep it in memory if they deem it necessary). That’s how expressions like:

"foo".length;
(7).toFixed();
7..toFixed(); // o primeiro ponto é o separador de casas decimais
true.valueOf();
  • So, in spite of 7 be the type Number, he uses the object Number, but it is not an instance of the same :\

  • 2

    Not quite. JS types are String, Number, Boolean, Null, Undefined and Object. The constructor Number (as in var n = new Number(1)) creates an instance of an object. The instanceof says who is the builder (or an ancestor of him in the prototype chain). The type of n is an object. The type of n.valueOf() is number. It became clearer?

  • Now I get it! It’s just that python for example, isinstance(1, int) returns True! I hoped that in the javascript was the same thing!

  • I don’t know much about Python, but this indicates that maybe there everything is object. In JS it’s not like that.

  • So the JS has the primitive types, which are not objects, but when accessed, are transformed into objects, but are still not objects. Is that right? Why all this confusion, why not just make everything objects (including the primitive ones)

6

Strings and Numbers are primitive values, not objects, and therefore do not have a [[Prototype]], so it will only work if you instantiate them as objects.

The same problem would occur in the case:

console.log("Texto" instanceof String); -> false

var texto = new String('3');
console.log(texto instanceof String) -> true

It has a very explanatory and good reference here in the OR

  • But how to explain that (7).toFixed(3) work, since they are primitive values? That’s what I wanted to understand in javascript. Because so much new Number(3).toFixed() and (3).toFixed() works?

  • (x) would not be an implicit cast?

  • Then I’d have to prove that 7 !== (7). For I have returned true for (7) === 7 and false for new Number(7) === 7

  • 1

    @Denie (x) is just an expression with parentheses to organize precedence, (x) === x.

  • Ah yes. So there is my doubt also why x.toFixed() error and the (x).toFixed() no, I really thought I was doing a cast implicit in it to make no mistake.

4

Simply because he "is not" a object instance.

Objection instances are declared using the keyword new.

The reported problem also occurs for the following situations:

"string" instanceof String;      // false
true     instanceof Boolean;     // false

The curious thing is that it doesn’t happen the same for the types array and Object:

({foo: "bar"}) instanceof Object;  // true
[1,2,3] instanceof Array;          // true

This is because objects really are objects in javascript, already the case of array is even more peculiar, because in Javascript arrays are objects, so much so that the following expression is true:

[1,2,3] instanceof Object; // true
typeof [1,2,3];            // object

Javascript is not (was) an object-oriented language, but rather a language oriented to prototypes (or prototypes of objects). MDN reads as follows::

In Javascript, inheritance occurs through prototype objects4 and defines a relation of type "is one" ("is a" Relationship). Each object inherits properties and methods of its prototype object which is referenced by the prototype property. MDN: Javascript object oriented

I mean, in your example:

Number.prototype.square = function ()
{
   return Math.pow(this, 2);
}

You are adding a method to the prototype of the object Number, that is, not just the objects Number's will inherit this method, as well as any "object" (typages and etc) that also inherits the prototype Number.

Some links about:

  • So, maybe this is more of a mistake than "having an explanation" since arrays work. And exactly why I asked the question: In javascript, everything is object!

  • But why did all my last examples "inherit" .square?

  • @Wallacemaxters complemented the answer to your question.

  • Thank you for the good will of all :)

Browser other questions tagged

You are not signed in. Login or sign up in order to post.