最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

javascript - Difference between reopen() and reopenClass() in Ember.js - Stack Overflow

programmeradmin0浏览0评论

I got confused while I was reading the documentation on emberjs

On the page above, it explains like this.

Person.reopen({
    // override `say` to add an ! at the end
    say: function(thing) {
    this._super(thing + "!");
    }
});

As you can see, reopen is used to add properties and methods to an instance. But when you need to create class method or add the properties to the class itself you can use reopenClass.

Person.reopenClass({
    createMan: function() {
    return Person.create({isMan: true})
    }
});

Person.createMan().get('isMan') // true

although the explanation says "reopen is used to add properties and methods to an instance.", I think both example shown above are talking about how to create class method or add the properties to the class itself, not to the instance.

Am I misunderstanding what it says? I'm not an experienced programmer, so I might be misunderstood...

please explain when to use reopen and reopenClass if I'm misunderstood.

Thanks in advance!

I got confused while I was reading the documentation on emberjs.com http://emberjs.com/documentation/#toc_reopening-classes-and-instances

On the page above, it explains like this.

Person.reopen({
    // override `say` to add an ! at the end
    say: function(thing) {
    this._super(thing + "!");
    }
});

As you can see, reopen is used to add properties and methods to an instance. But when you need to create class method or add the properties to the class itself you can use reopenClass.

Person.reopenClass({
    createMan: function() {
    return Person.create({isMan: true})
    }
});

Person.createMan().get('isMan') // true

although the explanation says "reopen is used to add properties and methods to an instance.", I think both example shown above are talking about how to create class method or add the properties to the class itself, not to the instance.

Am I misunderstanding what it says? I'm not an experienced programmer, so I might be misunderstood...

please explain when to use reopen and reopenClass if I'm misunderstood.

Thanks in advance!

Share Improve this question asked Dec 24, 2012 at 22:55 crzyonez777crzyonez777 1,8075 gold badges19 silver badges27 bronze badges 2
  • 1 this question may help you. – coderatchet Commented Mar 25, 2014 at 8:20
  • The simple answer is, use reopen when you want to add instance members, and reopenClass when you want to add static members to a class. – bentesha Commented May 15, 2018 at 16:47
Add a comment  | 

2 Answers 2

Reset to default 16

The documentation doesn't explain this very well, but it is a very tricky subject.

BTW, it now lives at: http://emberjs.com/guides/object-model/reopening-classes-and-instances/

One of the problems with talking about Object-Oriented Programming is that it's often explained like this: - Objects are Objects. Objects are instances of a class. - Classes are Objects. - Instances are Objects, and have a Class.

This explanation doesn't help anyone at all, and seems to be a recursive problem (ie there's no end to the referencing... An Object is an Instance of a Class which is an Object... (repeat)).

I prefer to reason in the following way:

When people write code, they often describe classes and instances. Classes are a type of thing. Fruit is an example of a class. We're not talking about a particular thing here, we're talking about a whole "class" of things (hence the name).

Note that it's not a real class. It's only real when it's "live" and "in memory in the computer". Until then, it's a description of a class. Usually when people write code, they write text in a text file, and that's just description of the real code inside the computer that happens when the computer interprets or compiles it into machine code.

The tricky bit comes when you realise that a class is actually itself a description, too. It's a description of a whole range of potentially real objects.

In the computer, when you create "an apple", that's an instance. It's also an object. Its class is Apple, which in a computer is a real live object, too. When we talk about Apple, that's an idea. It doesn't exist in reality, but for a computer to use something it must make it exist in its reality, so "Apple" is a concrete, real object, even though it's also an abstraction.

I think the last point is what gets people confused about objects. Classes are abstractions, but in order for the computer to talk and reason about them, they have to be made real. So, we decide... "class means abstract, instance means real"...

The trouble is, we have inheritance... which brings in the idea of layers of abstraction... so in our fruit model, you have the particular apple in front of you, which is also a Fruit, and Fruit is also a Food. In reality, Food doesn't actually exist as a thing or set of things, unless we say "this food, this apple", or "all the food in the world", or "your mum's lasagne", then it's an abstract idea...

So, in our object oriented computer, we say "define Food which is a kind of Object, now define Fruit which is a kind of Food, now define Apple which is a kind of Fruit, now define this apple, which is a kind of Apple".

Now that means: - Object is Food's class, and Food is an instance of Object, and Food is also itself a class! - Food is Fruit's class, and Fruit is an instance of Food, and Fruit is itself also a class! - Fruit is Apple's class, and Apple is an instance of Fruit, and Apple is also itself a class! - Apple is your apple's class, and your apple is an instance of Apple (and therefore also of Fruit, Food and Object!). However, it's NOT a class, it's just an object.

To reason about your apple, we'd say it's an object (note the lowercase o), it's also an Apple, and a Fruit and a Food, and... here's the kicker.. it's also an Object.

So now hopefully we're in a position where we can understand that your apple is an object, an instance (of Apple, Fruit, Food & Object), an Apple, a Fruit, a Food and an Object, but it's not a class.

So... if you add an instance method to a class, then it won't be available on the class, but it'll be available on all instances of that class. If you add a class method, it'll be available on that class (and sub-classes). So if you add an instance method to Apple, then all instances of apple will be able to run that method. If you add a method to only your apple, though, then only your apple will have that method. My apple won't. If you add a class method to Apple, then only the Apple class will be able to run that method (which, conveniently you can also access through all its instances). Class methods are for things which don't change PARTICULAR instances. Instance methods are for things which DO change PARTICULAR instances (generally). Same thing goes for properties/attributes. You wouldn't create a class method on the Apple class called "Apple colour" because that sounds like it relates to particular Apples (ie instances). Hopefully that clears things up a bit :)

After I experimented with reopen()and reopenClass(), I figured out the difference between them.

Here is the result from my experiment.

var Person = Ember.Object.extend({

    name:"",
    alive:true,
    sayHi:function(){
        alert("hi");
    }

});

Person.reopenClass({
    age:30,

    sayHo:function(){
    alert("ho");
}   

});

Person.reopen({
height:180,
sayYo:function(){
    alert("yo");
}
})

var person = Person.create({
    name:"Tom"
});


//person.reopenClass();//error!!

person.reopen({
    sayWhat:function(){
        alert("what!?");
    },

    weight:100

});

console.log(Person.alive);//undefined
console.log(Person.age);//30
console.log(Person.height);//undefined
console.log(Person.weight);//undefined

console.log(person.alive);//true
console.log(person.name);//Tom
console.log(person.height);//180
console.log(person.weight);//100

person.sayHi();//it works

//person.sayHo();//it doesn't work
Person.sayHo();//it works

person.sayYo();//it works
//Person.sayYo();//it doesn't work

//Person.sayWhat();//it doesn't work
person.sayWhat();
发布评论

评论列表(0)

  1. 暂无评论