JS进阶
__proto__ and prototype

李志业@FE
Inheritance

•

no classes!

•

prototype-based inheritance
__proto__
•

internal property, aka [[prototype]] !
•

the prototype of this object.!

•

exists internally, but hidden in...
1
2
3
4
5
6

var animal = { eats: true }!
var rabbit = { jumps: true }!
!
rabbit.__proto__ = animal // inherit!
!
alert(ra...
property search
[[Get]](P)
When the [[Get]] method of O is called with property
name P, the following steps are taken:!
1. If O doesn't ha...
new

new F() create object with!
!

obj.__proto__ = F.prototype
How
1. Create a new native ECMAScript object. !
2. The [[Prototype]] property of the newly constructed
object is set to th...
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17

function Animal() {!
this.eat = true;!
}!
var cat = new Animal();!
!
console.lo...
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17

function Animal() {!
this.eat = true;!
}!
var cat = new Animal();!
!
console.lo...
rabbit
rabbit
Animal
prototype
rabbit
Animal
prototype

{}
__proto__
rabbit
Animal
prototype

{}
__proto__

Object.prototype!
__proto__

null
new Animal()

rabbit

Animal
prototype

{}
__proto__

Object.prototype!
__proto__

null
cat
eats

TRUE

__proto__
new Animal()

rabbit

Animal
prototype

{}
__proto__

Object.prototype!
__proto__

null
cat
eats

TRUE

__proto__
new Animal()

rabbit

Animal
prototype

{}
{}
jump

TRUE

__proto__
__proto__

Object.prototype!...
cat
eats

TRUE

__proto__
new Animal()

rabbit

Animal
prototype

{}
{}
jump

{}
TRUE

bark

__proto__
__proto__

__proto_...
cat
eats

TRUE

__proto__
new Animal()

rabbit

Animal
prototype

{}
{}
jump

{}
TRUE

bark

__proto__
__proto__

__proto_...
cat
eats

dog
TRUE
__proto__

__proto__
new Animal()

rabbit

Animal
prototype

{}
{}
jump

{}
TRUE

bark

__proto__
__pro...
conclusion
•

search for property along the __proto__ chain!

•

property assign not affect the __proto__ property!

•

__...
Object.create
•

creates a new object with the specified prototype
object and properties.!

•

Syntax!
!

Object.create(pro...
1
2
3
4
5

var animal = { eats: true }!
rabbit = Object.create(animal);!
!
// true!
rabbit
console.log(rabbit.eats);!

rab...
1
2
3
4
5

var animal = { eats: true }!
rabbit = Object.create(animal);!
!
// true!
rabbit
console.log(rabbit.eats);!

ani...
1
2
3
4
5

var animal = { eats: true }!
rabbit = Object.create(animal);!
!
// true!
rabbit
console.log(rabbit.eats);!

ani...
1
2
3
4
5

var animal = { eats: true }!
rabbit = Object.create(animal);!
!
// true!
rabbit
console.log(rabbit.eats);!

ani...
rabbit
__proto__

1
2
3
4
5

var animal = { eats: true }!
rabbit = Object.create(animal);!
!
// true!
rabbit
console.log(r...
rabbit
__proto__

1
2
3
4
5

var animal = { eats: true }!
rabbit = Object.create(animal);!
!
// true!
rabbit
console.log(r...
How
Object.create ( O [, Properties] ) # Ⓣ Ⓡ!
1. If Type(O) is not Object or Null throw a TypeError exception.!
2. Let obj...
instanceof
logic behind obj instanceof F
1. Get obj.__proto__!
2. Compare obj.__proto__ against F.prototype!
3. If no matc...
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20

function Animal() {!
this.name = 'wangcai';!
}!
function Dog() {}!
Dog...
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20

function Animal() {!
this.name = 'wangcai';!
}!
function Dog() {}!
Dog...
Dog

d1
prototype

rabbit

__proto__

__proto__

Animal

Dog.prototype
name

‘wangcai’

__proto__

prototype
__proto__

An...
Dog

d1
prototype

rabbit

__proto__

__proto__

Dog.prototype
name

Dog.prototype

‘wangcai’

__proto__

name
__proto__

...
Will instanceof

always work?
Lies when cross window or iframe
1
2
3
4
5
6
7
8
9 !
10
11
12

<iframe id="fr" ></iframe>!
<script>!
var fr = document.getElementById('fr');!
var arr = [];...
1
2
3
4
5
6
7
8
9 !
10
11
12

<iframe id="fr" ></iframe>!
<script>!
var fr = document.getElementById('fr');!
var arr = [];...
Object.getPrototypeOf

•

preferred way to access the __proto__ of an object.!

•

readOnly
Reference
•

[[prototype]] http://blog.tsnrose.com/ecmascript262-3#_Prototype_!

•

Prototypal inheritance http://javascri...
Q&A

•

relation of __proto__ and prototype
  __proto__-and-prototype
Upcoming SlideShare
Loading in …5
×

__proto__-and-prototype

1,261 views

Published on

__proto__-and-prototype in javascript

Published in: Technology, Lifestyle
0 Comments
5 Likes
Statistics
Notes
  • Be the first to comment

No Downloads
Views
Total views
1,261
On SlideShare
0
From Embeds
0
Number of Embeds
182
Actions
Shares
0
Downloads
9
Comments
0
Likes
5
Embeds 0
No embeds

No notes for slide

__proto__-and-prototype

  1. 1. JS进阶 __proto__ and prototype 李志业@FE
  2. 2. Inheritance • no classes! • prototype-based inheritance
  3. 3. __proto__ • internal property, aka [[prototype]] ! • the prototype of this object.! • exists internally, but hidden in some browsers! • property search! • prototype chain: inheritance, instanceof
  4. 4. 1 2 3 4 5 6 var animal = { eats: true }! var rabbit = { jumps: true }! ! rabbit.__proto__ = animal // inherit! ! alert(rabbit.eats) // true!
  5. 5. property search
  6. 6. [[Get]](P) When the [[Get]] method of O is called with property name P, the following steps are taken:! 1. If O doesn't have a property with name P, go to step 4.! 2. Get the value of the property.! 3. Return Result(2).! 4. If the [[Prototype]] of O is null, return undefined.! 5. Call the [[Get]] method of [[Prototype]] with property name P.! 6. Return Result(5).
  7. 7. new new F() create object with! ! obj.__proto__ = F.prototype
  8. 8. How 1. Create a new native ECMAScript object. ! 2. The [[Prototype]] property of the newly constructed object is set to the Object prototype object. ! 3. The [[Class]] property of the newly constructed object is set to "Object". ! 4. The newly constructed object has no [[Value]] property. ! 5. Return the newly created native object.
  9. 9. 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 function Animal() {! this.eat = true;! }! var cat = new Animal();! ! console.log(cat.eat);! Animal.prototype.jump = true;! console.log(cat.jump);! ! Animal.prototype = {! bark: true! };! ! var dog = new Animal();! ! console.log(cat.bark);! console.log(dog.bark);!
  10. 10. 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 function Animal() {! this.eat = true;! }! var cat = new Animal();! ! console.log(cat.eat);! Animal.prototype.jump = true;! console.log(cat.jump);! ! Animal.prototype = {! bark: true! };! ! var dog = new Animal();! ! console.log(cat.bark);! console.log(dog.bark);! Run
  11. 11. rabbit
  12. 12. rabbit Animal prototype
  13. 13. rabbit Animal prototype {} __proto__
  14. 14. rabbit Animal prototype {} __proto__ Object.prototype! __proto__ null
  15. 15. new Animal() rabbit Animal prototype {} __proto__ Object.prototype! __proto__ null
  16. 16. cat eats TRUE __proto__ new Animal() rabbit Animal prototype {} __proto__ Object.prototype! __proto__ null
  17. 17. cat eats TRUE __proto__ new Animal() rabbit Animal prototype {} {} jump TRUE __proto__ __proto__ Object.prototype! __proto__ null
  18. 18. cat eats TRUE __proto__ new Animal() rabbit Animal prototype {} {} jump {} TRUE bark __proto__ __proto__ __proto__ Object.prototype! __proto__ null TRUE
  19. 19. cat eats TRUE __proto__ new Animal() rabbit Animal prototype {} {} jump {} TRUE bark __proto__ __proto__ __proto__ Object.prototype! __proto__ null TRUE
  20. 20. cat eats dog TRUE __proto__ __proto__ new Animal() rabbit Animal prototype {} {} jump {} TRUE bark __proto__ __proto__ __proto__ Object.prototype! __proto__ null TRUE
  21. 21. conclusion • search for property along the __proto__ chain! • property assign not affect the __proto__ property! • __proto__ was created at the moment of the object’s creation! • replacing prototype property of the constructor does not affect the prototype of already created objects
  22. 22. Object.create • creates a new object with the specified prototype object and properties.! • Syntax! ! Object.create(proto [, propertiesObject ])
  23. 23. 1 2 3 4 5 var animal = { eats: true }! rabbit = Object.create(animal);! ! // true! rabbit console.log(rabbit.eats);! rabbit
  24. 24. 1 2 3 4 5 var animal = { eats: true }! rabbit = Object.create(animal);! ! // true! rabbit console.log(rabbit.eats);! animal rabbit eat __proto__ TRUE
  25. 25. 1 2 3 4 5 var animal = { eats: true }! rabbit = Object.create(animal);! ! // true! rabbit console.log(rabbit.eats);! animal rabbit eat TRUE __proto__ Object.prototype! __proto__ null
  26. 26. 1 2 3 4 5 var animal = { eats: true }! rabbit = Object.create(animal);! ! // true! rabbit console.log(rabbit.eats);! animal rabbit eat TRUE __proto__ Object.prototype! __proto__ null
  27. 27. rabbit __proto__ 1 2 3 4 5 var animal = { eats: true }! rabbit = Object.create(animal);! ! // true! rabbit console.log(rabbit.eats);! animal rabbit eat TRUE __proto__ Object.prototype! __proto__ null
  28. 28. rabbit __proto__ 1 2 3 4 5 var animal = { eats: true }! rabbit = Object.create(animal);! ! // true! rabbit console.log(rabbit.eats);! animal rabbit eat TRUE __proto__ Object.prototype! __proto__ null
  29. 29. How Object.create ( O [, Properties] ) # Ⓣ Ⓡ! 1. If Type(O) is not Object or Null throw a TypeError exception.! 2. Let obj be the result of creating a new object as if by the expression new Object() where Object is the standard builtin constructor with that name! 3. Set the [[Prototype]] internal property of obj to O.! 4. If the argument Properties is present and not undefined, add own properties to obj as if by calling the standard built-in function Object.defineProperties with arguments obj and Properties.! 5. Return obj.
  30. 30. instanceof logic behind obj instanceof F 1. Get obj.__proto__! 2. Compare obj.__proto__ against F.prototype! 3. If no match then set temporarily obj = obj.__proto__ and repeat step 2 until either match is found or the chain ends.
  31. 31. 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 function Animal() {! this.name = 'wangcai';! }! function Dog() {}! Dog.prototype = new Animal();! ! var d1 = new Dog();! ! console.log(d1.name);! console.log(d1 instanceof Animal);! ! // change the prototype of Class! Dog.prototype = {! name: 'yingcai'! };! ! // now instanceof ??! console.log(d1 instanceof Dog);! console.log(d1 instanceof Animal);! console.log(Animal.prototype.__proto__ === Object.prototype);!
  32. 32. 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 function Animal() {! this.name = 'wangcai';! }! function Dog() {}! Dog.prototype = new Animal();! ! var d1 = new Dog();! ! console.log(d1.name);! console.log(d1 instanceof Animal);! ! // change the prototype of Class! Dog.prototype = {! name: 'yingcai'! };! ! // now instanceof ??! console.log(d1 instanceof Dog);! console.log(d1 instanceof Animal);! console.log(Animal.prototype.__proto__ === Object.prototype);! Run
  33. 33. Dog d1 prototype rabbit __proto__ __proto__ Animal Dog.prototype name ‘wangcai’ __proto__ prototype __proto__ Animal.prototype! __proto__ Function.prototype! __proto__ Object.prototype __proto__ null
  34. 34. Dog d1 prototype rabbit __proto__ __proto__ Dog.prototype name Dog.prototype ‘wangcai’ __proto__ name __proto__ Animal.prototype! __proto__ Object.prototype __proto__ null ‘wangcai’
  35. 35. Will instanceof always work?
  36. 36. Lies when cross window or iframe
  37. 37. 1 2 3 4 5 6 7 8 9 ! 10 11 12 <iframe id="fr" ></iframe>! <script>! var fr = document.getElementById('fr');! var arr = [];! var ArrayFr = fr.contentWindow.Array;! var arr2 = new ArrayFr();! console.log(Object.prototype.toString.call(arr));! console.log(Object.prototype.toString.call(arr2));! console.log(arr instanceof Array);! console.log(arr instanceof ArrayFr);! </script>!
  38. 38. 1 2 3 4 5 6 7 8 9 ! 10 11 12 <iframe id="fr" ></iframe>! <script>! var fr = document.getElementById('fr');! var arr = [];! var ArrayFr = fr.contentWindow.Array;! var arr2 = new ArrayFr();! console.log(Object.prototype.toString.call(arr));! console.log(Object.prototype.toString.call(arr2));! console.log(arr instanceof Array);! console.log(arr instanceof ArrayFr);! </script>! Run
  39. 39. Object.getPrototypeOf • preferred way to access the __proto__ of an object.! • readOnly
  40. 40. Reference • [[prototype]] http://blog.tsnrose.com/ecmascript262-3#_Prototype_! • Prototypal inheritance http://javascript.info/tutorial/inheritance ! • http://dmitrysoshnikov.com/ecmascript/chapter-7-2-oop-ecmascriptimplementation/#prototype! • [[Get]](P) http://blog.tsnrose.com/ecmascript262-3#a-8.6.2.1! • new Object() http://blog.tsnrose.com/ecmascript262-3#a-15.2.2.1
  41. 41. Q&A • relation of __proto__ and prototype

×