2

Possible Duplicate:
How to detect if a function is called as constructor?

I would like to have a function in JavaScript which behaves differently if it's called normally or if it's invoked in order to create a new instance. There could be many different uses, where the two functionalities can be related or not related. One use would be to exempt the coder from having to type new, when the function is always used to create new instances:

function MyClass(arg1, arg2) {
  if(/* not called with "new" */) return new MyClass(arg1, arg2);

  // instance initialization stuff here...

}

This way I wouldn't have to type var x = new MyClass(arg1, arg2): it would be enough to type var x = MyClass(arg1, arg2) (but the former wouldn't be wrong either).

Just one example of a possible use.

Can this be done? If so, how?

Community
  • 1
  • 1
Tom
  • 4,910
  • 5
  • 33
  • 48
  • Sorry for missing the duplicate - I should have looked for the keyword "constructor"... Thanks for the answers! – Tom Jul 25 '12 at 00:45

3 Answers3

5

There is no way to be absolutely sure how the function was called, but you can be pretty sure using this instanceof MyClass, like so:

if (this instanceof MyClass) {
    // Was called with `new`
} else {
    // Was called as regular function
}

There are edge cases though, e.g. I could create a new instance of MyClass and then do MyClass.call(new MyClass) -- this would create a false positive, as the outer MyClass was not called with new.

James
  • 109,676
  • 31
  • 162
  • 175
  • I took this as a basis, and added a twist: when initializing a new instance I set a flag on it. So when the function is called I check 1) that `this` is `instanceof` my class, and 2) that its flag is still not set. If both conditions hold - it's `new` (in which case I set the flag and do whatever else I do). If not, I know it's an ordinary function call (even if from another method of the class). – Tom Aug 02 '12 at 20:13
1

The only option I can think of here is to test the value of this. You might try:

function MyClass(args) {
    var isInstance = this instanceof MyClass;
    // ...
}
nrabinowitz
  • 55,314
  • 10
  • 149
  • 165
1
if(this instanceof MyClass)

is probably what you're looking for. It can be fooled with .call and .apply, but there shouldn't be any problem constructing the object if an instance is passed, anyway.

Ry-
  • 218,210
  • 55
  • 464
  • 476