Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

TypeError: this.prototype is undefined when calling Function.prototype.method()

I am reading the book "Javascript: The good parts".
Now I am reading chapter about Augmenting Types:

Function.prototype.method = function (name, func) {
   this.prototype[name] = func;
   return this;
};

UPDATE:
Why following code does not work?

js> Function.prototype.method("test", function(){print("TEST")});
typein:2: TypeError: this.prototype is undefined

But following code works without problems:

js> Function.method("test", function(){print("TEST")});
function Function() {[native code]}

Why this code works?

js> var obj = {"status" : "ST"};
js> typeof obj;
"object"
js> obj.method = function(){print(this.status)};
(function () {print(this.status);})
js> obj.method();
ST

"obj" is object.
But I can call method "method" on it.
What is the difference between Function.prototype.method and obj.method?

like image 553
Volodymyr Bezuglyy Avatar asked Feb 08 '12 18:02

Volodymyr Bezuglyy


People also ask

Why is prototype undefined?

The prototype property only exists on functions, and person is not a function. It's an object .

How to create a Prototype in JavaScript?

Object's PrototypeUse Object. getPrototypeOf(obj) method instead of __proto__ to access prototype object. The prototype object includes following properties and methods. Returns a function that created instance.

How to define this in JavaScript?

In JavaScript, the this keyword refers to an object. Which object depends on how this is being invoked (used or called). The this keyword refers to different objects depending on how it is used: In an object method, this refers to the object.

What is the prototype chain in js?

Each object has a private property which holds a link to another object called its prototype. That prototype object has a prototype of its own, and so on until an object is reached with null as its prototype. By definition, null has no prototype, and acts as the final link in this prototype chain.


2 Answers

this refers to Function.prototype because you called .method on that. So, you're using Function.prototype.prototype which does not exist.

Either use Function.method(...) or this[name] = ... to eliminate one of the .prototypes.

like image 103
pimvdb Avatar answered Oct 01 '22 15:10

pimvdb


Because:

Function instanceof Function           // <--- is true
Function.prototype instanceof Function // <-- is false
  • Function.prototype is an Object, and does not inherit anything from the Function contructor.
  • Function is a constructor, but also a function, so it inherits methods from Function.prototype.

  • When calling Function.method, you're calling the method method of an instance of Function. So, this points to the created instance of Function.
  • When calling Function.prototype.method, you're invoking an ordinary method of an object. this points to Function.prototype.

To clarify, here's an example:

Function.method()                // is equivalent to
(function Function(){}).method()
(new Function).method()          // Because Function is also a function

Function.prototype.method // No instance, just a plain function call
like image 21
Rob W Avatar answered Oct 01 '22 14:10

Rob W