JavaScript面向对象编程[转]

JavaScript面向对象编程

命名空间

命名空间是一个容器,它允许开发人员在一个独特的,特定于应用程序的名称下捆绑所有的功能。 在JavaScript中,命名空间只是另一个包含方法,属性,对象的对象。

需要认识到非常重要的一点,与其他面向对象编程语言中的普通对象和命名空间相比,它们在语言层面上没有区别。

创造的JavaScript命名空间背后的想法很简单:一个全局对象被创建,所有的变量,方法和功能成为该对象的属性。使用命名空间也最大程度地减少应用程序的名称冲突的可能性。

我们来创建一个全局变量叫做 MYAPP


1

2

<code class=" language-js"><span class="token comment">// 全局命名空间

<span class="token keyword">var MYAPP <span class="token operator">= MYAPP <span class="token operator">|| <span class="token punctuation">{<span class="token punctuation">}<span class="token punctuation">;</span></span></span></span></span></span></span></code>

 

在上面的代码示例中,我们首先检查MYAPP是否已经被定义(是否在同一文件中或在另一文件)。如果是的话,那么使用现有的MYAPP全局对象,否则,创建一个名为MYAPP的空对象用来封装方法,函数,变量和对象。

我们也可以创建子命名空间:


1

2

<code class=" language-js"><span class="token comment">// 子命名空间

MYAPP<span class="token punctuation">.event <span class="token operator">= <span class="token punctuation">{<span class="token punctuation">}<span class="token punctuation">;</span></span></span></span></span></span></code>

 

下面是用于创建命名空间和添加变量,函数和方法的代码写法:


1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

<code class=" language-js"><span class="token comment">// 给普通方法和属性创建一个叫做MYAPP.commonMethod的容器

MYAPP<span class="token punctuation">.commonMethod <span class="token operator">= <span class="token punctuation">{

  regExForName<span class="token punctuation">: <span class="token string">""<span class="token punctuation">,<span class="token comment"> // 定义名字的正则验证

  regExForPhone<span class="token punctuation">: <span class="token string">""<span class="token punctuation">,<span class="token comment"> // 定义电话的正则验证

  validateName<span class="token punctuation">: <span class="token keyword">function<span class="token punctuation">(name<span class="token punctuation">)<span class="token punctuation">{

   <span class="token comment"> // 对名字name做些操作,你可以通过使用“this.regExForname”

   <span class="token comment"> // 访问regExForName变量

  <span class="token punctuation">}<span class="token punctuation">,

  

  validatePhoneNo<span class="token punctuation">: <span class="token keyword">function<span class="token punctuation">(phoneNo<span class="token punctuation">)<span class="token punctuation">{

   <span class="token comment"> // 对电话号码做操作

  <span class="token punctuation">}

<span class="token punctuation">}

<span class="token comment">

// 对象和方法一起申明

MYAPP<span class="token punctuation">.event <span class="token operator">= <span class="token punctuation">{

    addListener<span class="token punctuation">: <span class="token keyword">function<span class="token punctuation">(el<span class="token punctuation">, type<span class="token punctuation">, fn<span class="token punctuation">) <span class="token punctuation">{

   <span class="token comment"> //  代码

    <span class="token punctuation">}<span class="token punctuation">,

   removeListener<span class="token punctuation">: <span class="token keyword">function<span class="token punctuation">(el<span class="token punctuation">, type<span class="token punctuation">, fn<span class="token punctuation">) <span class="token punctuation">{

   <span class="token comment"> // 代码

   <span class="token punctuation">}<span class="token punctuation">,

   getEvent<span class="token punctuation">: <span class="token keyword">function<span class="token punctuation">(e<span class="token punctuation">) <span class="token punctuation">{

  <span class="token comment"> // 代码

   <span class="token punctuation">}

   

  <span class="token comment"> // 还可以添加其他的属性和方法

<span class="token punctuation">}

<span class="token comment">

//使用addListner方法的写法:

MYAPP<span class="token punctuation">.event<span class="token punctuation">.<span class="token function">addListener<span class="token punctuation">(<span class="token string">"yourel"<span class="token punctuation">, <span class="token string">"type"<span class="token punctuation">, callback<span class="token punctuation">)<span class="token punctuation">;</span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></code>

 

标准内置对象

JavaScript有包括在其核心的几个对象,例如,Math,Object,Array和String对象。下面的例子演示了如何使用Math对象使用其随机()方法来获得一个随机数。


1

<code class=" language-js">console<span class="token punctuation">.<span class="token function">log<span class="token punctuation">(Math<span class="token punctuation">.<span class="token function">random<span class="token punctuation">(<span class="token punctuation">)<span class="token punctuation">)<span class="token punctuation">;</span></span></span></span></span></span></span></span></span></code>

 

注意:T这里和接下来的例子都假设名为 console.log 的方法全局有定义。console.log 实际上不是 JavaScript 自带的。

查看 JavaScript 参考:全局对象 了解 JavaScript 内置对象的列表。

JavaScript 中的每个对象都是 Object 对象的实例且继承它所有的属性和方法。

自定义对象

JavaScript是一种基于原型的语言,它没类的声明语句,比如C+ +或Java中用的。这有时会对习惯使用有类申明语句语言的程序员产生困扰。相反,JavaScript可用方法作类。定义一个类跟定义一个函数一样简单。在下面的例子中,我们定义了一个新类Person。


1

2

3

<code class=" language-js"><span class="token keyword">function <span class="token function">Person<span class="token punctuation">(<span class="token punctuation">) <span class="token punctuation">{ <span class="token punctuation">} <span class="token comment">

// 或

<span class="token keyword">var Person <span class="token operator">= <span class="token keyword">function<span class="token punctuation">(<span class="token punctuation">)<span class="token punctuation">{ <span class="token punctuation">}</span></span></span></span></span></span></span></span></span></span></span></span></span></span></code>

 

对象(类的实例)

我们使用 new obj 创建对象 obj 的新实例, 将结果(obj 类型)赋值给一个变量方便稍后调用。

在下面的示例中,我们定义了一个名为Person的类,然后我们创建了两个Person的实例(person1 and person2).


1

2

3

<code class=" language-js"><span class="token keyword">function <span class="token function">Person<span class="token punctuation">(<span class="token punctuation">) <span class="token punctuation">{ <span class="token punctuation">}

<span class="token keyword">var person1 <span class="token operator">= <span class="token keyword">new <span class="token class-name">Person<span class="token punctuation">(<span class="token punctuation">)<span class="token punctuation">;

<span class="token keyword">var person2 <span class="token operator">= <span class="token keyword">new <span class="token class-name">Person<span class="token punctuation">(<span class="token punctuation">)<span class="token punctuation">;</span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></code>

 

有两种为对象创建实例,请参考 Object.create 。

构造器

在实例化时构造器被调用 (也就是对象实例被创建时)。构造器是对象中的一个方法。 在JavaScript,中函数就可以作为构造器使用,因此不需要特别地定义一个构造器方法. 每个声明的函数都可以在实例化后被调用执行

构造器常用于给对象的属性赋值或者为调用函数做准备。 在本文的后面描述了类中方法既可以在定义时添加,也可以在使用前添加。

在下面的示例中, Person类实例化时构造器调用一个 alert函数。


1

2

3

4

5

6

<code class=" language-js"><span class="token keyword">function <span class="token function">Person<span class="token punctuation">(<span class="token punctuation">) <span class="token punctuation">{

  <span class="token function">alert<span class="token punctuation">(<span class="token string">'Person instantiated'<span class="token punctuation">)<span class="token punctuation">;

<span class="token punctuation">}

 

<span class="token keyword">var person1 <span class="token operator">= <span class="token keyword">new <span class="token class-name">Person<span class="token punctuation">(<span class="token punctuation">)<span class="token punctuation">;

<span class="token keyword">var person2 <span class="token operator">= <span class="token keyword">new <span class="token class-name">Person<span class="token punctuation">(<span class="token punctuation">)<span class="token punctuation">;</span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></code>

 

属性 (对象属性)

属性就是 类中包含的变量;每一个对象实例有若干个属性. 为了正确的继承,属性应该被定义在类的原型属性 (函数)中。

可以使用 关键字 this调用类中的属性, this是对当前对象的引用。 从外部存取(读/写)其属性的语法是: InstanceName.Property; 这与C++,Java或者许多其他语言中的语法是一样的 (在类中语法 this.Property 常用于set和get属性值)

在下面的示例中,我们为定义Person类定义了一个属性 firstName 并在实例化时赋初值。


1

2

3

4

5

6

7

8

9

10

11

<code class=" language-js"><span class="token keyword">function <span class="token function">Person<span class="token punctuation">(firstName<span class="token punctuation">) <span class="token punctuation">{

  <span class="token keyword">this<span class="token punctuation">.firstName <span class="token operator">= firstName<span class="token punctuation">;

  <span class="token function">alert<span class="token punctuation">(<span class="token string">'Person instantiated'<span class="token punctuation">)<span class="token punctuation">;

<span class="token punctuation">}

 

<span class="token keyword">var person1 <span class="token operator">= <span class="token keyword">new <span class="token class-name">Person<span class="token punctuation">(<span class="token string">'Alice'<span class="token punctuation">)<span class="token punctuation">;

<span class="token keyword">var person2 <span class="token operator">= <span class="token keyword">new <span class="token class-name">Person<span class="token punctuation">(<span class="token string">'Bob'<span class="token punctuation">)<span class="token punctuation">;

<span class="token comment">

// Show the firstName properties of the objects

<span class="token function">alert<span class="token punctuation">(<span class="token string">'person1 is '<span class="token operator">+ person1<span class="token punctuation">.firstName<span class="token punctuation">)<span class="token punctuation">;<span class="token comment"> // alerts "person1 is Alice"

<span class="token function">alert<span class="token punctuation">(<span class="token string">'person2 is '<span class="token operator">+ person2<span class="token punctuation">.firstName<span class="token punctuation">)<span class="token punctuation">;<span class="token comment"> // alerts "person2 is Bob"</span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></code>

 

方法

方法与属性很相似, 不同的是:一个是函数,另一个可以被定义为函数。 调用方法很像存取一个属性,  不同的是add () 在方法名后面很可能带着参数. 为定义一个方法, 需要将一个函数赋值给类的 prototype 属性; 这个赋值给函数的名称就是用来给对象在外部调用它使用的。

在下面的示例中,我们给Person类定义了方法 sayHello(),并调用了它.


1

2

3

4

5

6

7

8

9

10

11

12

13

14

<code class=" language-js"><span class="token keyword">function <span class="token function">Person<span class="token punctuation">(firstName<span class="token punctuation">) <span class="token punctuation">{

  <span class="token keyword">this<span class="token punctuation">.firstName <span class="token operator">= firstName<span class="token punctuation">;

<span class="token punctuation">}

 

Person<span class="token punctuation">.prototype<span class="token punctuation">.sayHello <span class="token operator">= <span class="token keyword">function<span class="token punctuation">(<span class="token punctuation">) <span class="token punctuation">{

  <span class="token function">alert<span class="token punctuation">(<span class="token string">"Hello, I'm " <span class="token operator">+ <span class="token keyword">this<span class="token punctuation">.firstName<span class="token punctuation">)<span class="token punctuation">;

<span class="token punctuation">}<span class="token punctuation">;

 

<span class="token keyword">var person1 <span class="token operator">= <span class="token keyword">new <span class="token class-name">Person<span class="token punctuation">(<span class="token string">"Alice"<span class="token punctuation">)<span class="token punctuation">;

<span class="token keyword">var person2 <span class="token operator">= <span class="token keyword">new <span class="token class-name">Person<span class="token punctuation">(<span class="token string">"Bob"<span class="token punctuation">)<span class="token punctuation">;

<span class="token comment">

// call the Person sayHello method.

person1<span class="token punctuation">.<span class="token function">sayHello<span class="token punctuation">(<span class="token punctuation">)<span class="token punctuation">;<span class="token comment"> // alerts "Hello, I'm Alice"

person2<span class="token punctuation">.<span class="token function">sayHello<span class="token punctuation">(<span class="token punctuation">)<span class="token punctuation">;<span class="token comment"> // alerts "Hello, I'm Bob"</span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></code>

 

在JavaScript中方法通常是一个绑定到对象中的普通函数, 这意味着方法可以在其所在context之外被调用。 思考下面示例中的代码:


1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

<code class=" language-js"><span class="token keyword">function <span class="token function">Person<span class="token punctuation">(firstName<span class="token punctuation">) <span class="token punctuation">{

  <span class="token keyword">this<span class="token punctuation">.firstName <span class="token operator">= firstName<span class="token punctuation">;

<span class="token punctuation">}

 

Person<span class="token punctuation">.prototype<span class="token punctuation">.sayHello <span class="token operator">= <span class="token keyword">function<span class="token punctuation">(<span class="token punctuation">) <span class="token punctuation">{

  <span class="token function">alert<span class="token punctuation">(<span class="token string">"Hello, I'm " <span class="token operator">+ <span class="token keyword">this<span class="token punctuation">.firstName<span class="token punctuation">)<span class="token punctuation">;

<span class="token punctuation">}<span class="token punctuation">;

 

<span class="token keyword">var person1 <span class="token operator">= <span class="token keyword">new <span class="token class-name">Person<span class="token punctuation">(<span class="token string">"Alice"<span class="token punctuation">)<span class="token punctuation">;

<span class="token keyword">var person2 <span class="token operator">= <span class="token keyword">new <span class="token class-name">Person<span class="token punctuation">(<span class="token string">"Bob"<span class="token punctuation">)<span class="token punctuation">;

<span class="token keyword">var helloFunction <span class="token operator">= person1<span class="token punctuation">.sayHello<span class="token punctuation">;

 

person1<span class="token punctuation">.<span class="token function">sayHello<span class="token punctuation">(<span class="token punctuation">)<span class="token punctuation">;                                <span class="token comment"> // alerts "Hello, I'm Alice"

person2<span class="token punctuation">.<span class="token function">sayHello<span class="token punctuation">(<span class="token punctuation">)<span class="token punctuation">;                                <span class="token comment"> // alerts "Hello, I'm Bob"

<span class="token function">helloFunction<span class="token punctuation">(<span class="token punctuation">)<span class="token punctuation">;                                   <span class="token comment"> // alerts "Hello, I'm undefined" (or fails

                                                   <span class="token comment"> // with a TypeError in strict mode)

<span class="token function">alert<span class="token punctuation">(helloFunction <span class="token operator">=== person1<span class="token punctuation">.sayHello<span class="token punctuation">)<span class="token punctuation">;         <span class="token comment"> // alerts true

<span class="token function">alert<span class="token punctuation">(helloFunction <span class="token operator">=== Person<span class="token punctuation">.prototype<span class="token punctuation">.sayHello<span class="token punctuation">)<span class="token punctuation">;<span class="token comment"> // alerts true

helloFunction<span class="token punctuation">.<span class="token function">call<span class="token punctuation">(person1<span class="token punctuation">)<span class="token punctuation">;                       <span class="token comment"> // alerts "Hello, I'm Alice"</span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></code>

 

如上例所示, 所有指向sayHello函数的引用 ,包括 person1Person.prototype, 和 helloFunction 等, 均引用了相同的函数.

在调用函数的过程中,this的值取决于我们怎么样调用函数.  在通常情况下,我们通过一个表达式person1.sayHello()来调用函数:即从一个对象的属性中得到所调用的函数。此时this被设置为我们取得函数的对象(即person1)。这就是为什么person1.sayHello() 使用了姓名“Alice”而person2.sayHello()使用了姓名“bob”的原因。 

然而我们使用不同的调用方法时, this的值也就不同了。当从变量 helloFunction()中调用的时候, this就被设置成了全局对象 (在浏览器中即window)。由于该对象 (非常可能地) 没有firstName 属性, 我们得到的结果便是"Hello, I'm undefined". (这是松散模式下的结果, 在 严格模式中,结果将不同(此时会产生一个error)。 但是为了避免混淆,我们在这里不涉及细节) 。另外,我们可以像上例末尾那样,使用Function#call (或者Function#apply)显式的设置this的值。

更多有关信息请参考 Function#call and Function#apply

继承

创建一个或多个类的专门版本类方式称为继承(Javascript只支持单继承)。 创建的专门版本的类通常叫做子类,另外的类通常叫做父类。 在Javascript中,继承通过赋予子类一个父类的实例并专门化子类来实现。在现代浏览器中你可以使用 Object.create 实现继承.

JavaScript 并不检测子类的 prototype.constructor (见 Object.prototype), 所以我们必须手动申明它.

在下面的例子中, 我们定义了 Student类作为 Person类的子类. 之后我们重定义了sayHello() 方法并添加了 sayGoodBye() 方法.


1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

37

38

39

40

41

42

43

44

45

46

47

48

49

50

51

<code class=" language-js"><span class="token comment">// 定义Person构造器

<span class="token keyword">function <span class="token function">Person<span class="token punctuation">(firstName<span class="token punctuation">) <span class="token punctuation">{

  <span class="token keyword">this<span class="token punctuation">.firstName <span class="token operator">= firstName<span class="token punctuation">;

<span class="token punctuation">}

<span class="token comment">

// 在Person.prototype中加入方法

Person<span class="token punctuation">.prototype<span class="token punctuation">.walk <span class="token operator">= <span class="token keyword">function<span class="token punctuation">(<span class="token punctuation">)<span class="token punctuation">{

  <span class="token function">alert<span class="token punctuation">(<span class="token string">"I am walking!"<span class="token punctuation">)<span class="token punctuation">;

<span class="token punctuation">}<span class="token punctuation">;

Person<span class="token punctuation">.prototype<span class="token punctuation">.sayHello <span class="token operator">= <span class="token keyword">function<span class="token punctuation">(<span class="token punctuation">)<span class="token punctuation">{

  <span class="token function">alert<span class="token punctuation">(<span class="token string">"Hello, I'm " <span class="token operator">+ <span class="token keyword">this<span class="token punctuation">.firstName<span class="token punctuation">)<span class="token punctuation">;

<span class="token punctuation">}<span class="token punctuation">;

<span class="token comment">

// 定义Student构造器

<span class="token keyword">function <span class="token function">Student<span class="token punctuation">(firstName<span class="token punctuation">, subject<span class="token punctuation">) <span class="token punctuation">{

 <span class="token comment"> // 调用父类构造器, 确保(使用Function#call)"this" 在调用过程中设置正确

  Person<span class="token punctuation">.<span class="token function">call<span class="token punctuation">(<span class="token keyword">this<span class="token punctuation">, firstName<span class="token punctuation">)<span class="token punctuation">;

 

 <span class="token comment"> // 初始化Student类特有属性

  <span class="token keyword">this<span class="token punctuation">.subject <span class="token operator">= subject<span class="token punctuation">;

<span class="token punctuation">}<span class="token punctuation">;

<span class="token comment">

// 建立一个由Person.prototype继承而来的Student.prototype对象.

<span class="token comment">// 注意: 常见的错误是使用 "new Person()"来建立Student.prototype.

<span class="token comment">// 这样做的错误之处有很多, 最重要的一点是我们在实例化时

<span class="token comment">// 不能赋予Person类任何的FirstName参数

<span class="token comment">// 调用Person的正确位置如下,我们从Student中来调用它

Student<span class="token punctuation">.prototype <span class="token operator">= Object<span class="token punctuation">.<span class="token function">create<span class="token punctuation">(Person<span class="token punctuation">.prototype<span class="token punctuation">)<span class="token punctuation">;<span class="token comment"> // See note below

<span class="token comment">

// 设置"constructor" 属性指向Student

Student<span class="token punctuation">.prototype<span class="token punctuation">.constructor <span class="token operator">= Student<span class="token punctuation">;

<span class="token comment">

// 更换"sayHello" 方法

Student<span class="token punctuation">.prototype<span class="token punctuation">.sayHello <span class="token operator">= <span class="token keyword">function<span class="token punctuation">(<span class="token punctuation">)<span class="token punctuation">{

  <span class="token function">alert<span class="token punctuation">(<span class="token string">"Hello, I'm " <span class="token operator">+ <span class="token keyword">this<span class="token punctuation">.firstName <span class="token operator">+ <span class="token string">". I'm studying " <span class="token operator">+ <span class="token keyword">this<span class="token punctuation">.subject <span class="token operator">+ <span class="token string">"."<span class="token punctuation">)<span class="token punctuation">;

<span class="token punctuation">}<span class="token punctuation">;

<span class="token comment">

// 加入"sayGoodBye" 方法

Student<span class="token punctuation">.prototype<span class="token punctuation">.sayGoodBye <span class="token operator">= <span class="token keyword">function<span class="token punctuation">(<span class="token punctuation">)<span class="token punctuation">{

  <span class="token function">alert<span class="token punctuation">(<span class="token string">"Goodbye!"<span class="token punctuation">)<span class="token punctuation">;

<span class="token punctuation">}<span class="token punctuation">;

<span class="token comment">

// 测试实例:

<span class="token keyword">var student1 <span class="token operator">= <span class="token keyword">new <span class="token class-name">Student<span class="token punctuation">(<span class="token string">"Janet"<span class="token punctuation">, <span class="token string">"Applied Physics"<span class="token punctuation">)<span class="token punctuation">;

student1<span class="token punctuation">.<span class="token function">sayHello<span class="token punctuation">(<span class="token punctuation">)<span class="token punctuation">;  <span class="token comment"> // "Hello, I'm Janet. I'm studying Applied Physics."

student1<span class="token punctuation">.<span class="token function">walk<span class="token punctuation">(<span class="token punctuation">)<span class="token punctuation">;      <span class="token comment"> // "I am walking!"

student1<span class="token punctuation">.<span class="token function">sayGoodBye<span class="token punctuation">(<span class="token punctuation">)<span class="token punctuation">;<span class="token comment"> // "Goodbye!"

<span class="token comment">

// Check that instanceof works correctly

<span class="token function">alert<span class="token punctuation">(student1 <span class="token keyword">instanceof <span class="token class-name">Person<span class="token punctuation">)<span class="token punctuation">; <span class="token comment"> // true

<span class="token function">alert<span class="token punctuation">(student1 <span class="token keyword">instanceof <span class="token class-name">Student<span class="token punctuation">)<span class="token punctuation">;<span class="token comment"> // true</span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></code>

 

对于“Student.prototype = Object.create(Person.prototype);”这一行,在不支持 Object.create方法的老JavaScript引擎中,可以使用一个"polyfill"(又名"shim",查看文章链接),或者使用一个function来获得相同的返回值,就像下面:


1

2

3

4

5

6

7

8

<code class=" language-js"><span class="token keyword">function <span class="token function">createObject<span class="token punctuation">(proto<span class="token punctuation">) <span class="token punctuation">{

    <span class="token keyword">function <span class="token function">ctor<span class="token punctuation">(<span class="token punctuation">) <span class="token punctuation">{ <span class="token punctuation">}

    ctor<span class="token punctuation">.prototype <span class="token operator">= proto<span class="token punctuation">;

    <span class="token keyword">return <span class="token keyword">new <span class="token class-name">ctor<span class="token punctuation">(<span class="token punctuation">)<span class="token punctuation">;

<span class="token punctuation">}

<span class="token comment">

// Usage:

Student<span class="token punctuation">.prototype <span class="token operator">= <span class="token function">createObject<span class="token punctuation">(Person<span class="token punctuation">.prototype<span class="token punctuation">)<span class="token punctuation">;</span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></code>

 

更多相关信息请参考 Object.create,连接中还有一个老JavaScript引擎的兼容方案(shim)。

封装

在上一个例子中,Student类虽然不需要知道Person类的walk()方法是如何实现的,但是仍然可以使用这个方法;Student类不需要明确地定义这个方法,除非我们想改变它。 这就叫做封装,对于所有继承自父类的方法,只需要在子类中定义那些你想改变的即可。

抽象

抽象是允许模拟工作问题中通用部分的一种机制。这可以通过继承(具体化)或组合来实现。
JavaScript通过继承实现具体化,通过让类的实例是其他对象的属性值来实现组合。

JavaScript Function 类继承自Object类(这是典型的具体化) 。Function.prototype的属性是一个Object实例(这是典型的组合)。


1

2

3

<code class=" language-js"><span class="token keyword">var foo <span class="token operator">= <span class="token keyword">function<span class="token punctuation">(<span class="token punctuation">)<span class="token punctuation">{<span class="token punctuation">}<span class="token punctuation">;

<span class="token function">alert<span class="token punctuation">( <span class="token string">'foo is a Function: ' <span class="token operator">+ <span class="token punctuation">(foo <span class="token keyword">instanceof <span class="token class-name">Function<span class="token punctuation">) <span class="token punctuation">)<span class="token punctuation">;                 <span class="token comment"> // alerts "foo is a Function: true"

<span class="token function">alert<span class="token punctuation">( <span class="token string">'foo.prototype is an Object: ' <span class="token operator">+ <span class="token punctuation">(foo<span class="token punctuation">.prototype <span class="token keyword">instanceof <span class="token class-name">Object<span class="token punctuation">) <span class="token punctuation">)<span class="token punctuation">;<span class="token comment"> // alerts "foo.prototype is an Object: true"</span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></code>

 

多态

就像所有定义在原型属性内部的方法和属性一样,不同的类可以定义具有相同名称的方法;方法是作用于所在的类中。并且这仅在两个类不是父子关系时成立(继承链中,一个类不是继承自其他类)。

注意

本文中所展示的面向对象编程技术不是唯一的实现方式,在JavaScript中面向对象的实现是非常灵活的。

同样的,文中展示的技术没有使用任何语言hacks,它们也没有模仿其他语言的对象理论实现。

JavaScript中还有其他一些更加先进的面向对象技术,但这些都超出了本文的介绍范围。

 

文章出处:https://developer.mozilla.org/zh-CN/docs/Web/JavaScript/Introduction_to_Object-Oriented_JavaScript

欢迎加群互相学习,共同进步。QQ群:iOS: 58099570 | Android: 330987132 | Go:217696290 | Python:336880185 | 做人要厚道,转载请注明出处!http://www.cnblogs.com/sunshine-anycall/p/4414045.html

时间: 2024-09-21 05:00:02

JavaScript面向对象编程[转]的相关文章

js面向对象 编程: JavaScript 面向对象编程,严格过程的标准化编程法,目前为止最好的 JS 生成对象代码结构

市面上流行了很多 JavaScript 面向对象的编程方法,其中不少都有好些问题.这里总结最正确的 JavaScript 面向对象编程模式.对于类 Special 继承自类 Common 继承自类 Super 的情况,一个 Special 对象的创建,详细说来,应该经历以下步骤.1 确定继承关系1.1 读取 Special 的父类,发现是 Common1.2 读取 Common 的父类,发现是 Super1.3 读取 Super 的父类,发现没有了(隐形父类 Object)2 加载类结构(如果没

深入剖析JavaScript面向对象编程_javascript技巧

二. Javascript 面向对象编程:构造函数的继承 本节主要介绍,如何生成一个"继承"多个对象的实例. 比如,现在有一个"动物"对象的构造函数, function Animal(){ this.species = "动物"; } 还有一个"猫"对象的构造函数, function Cat(name,color){ this.name = name; this.color = color; } 怎样才能使"猫&qu

Javascript 面向对象编程

Javascript 面向对象编程 2012年1月9日陈皓 发表评论阅读评论 49,161 人阅读     Javascript是一个类C的语言,他的面向对象的东西相对于C++/Java比较奇怪,但是其的确相当的强大,在 Todd 同学的"对象的消息模型"一文中我们已经可以看到一些端倪了.这两天有个前同事总在问我Javascript面向对象的东西,所以,索性写篇文章让他看去吧,这里这篇文章主要想从一个整体的角度来说明一下Javascript的面向对象的编程.(成文比较仓促,应该有不准确

Javascript 面向对象编程(一):封装

Javascript 面向对象编程(一):封装  作者: 阮一峰 日期: 2010年5月17日 学习Javascript,最难的地方是什么? 我觉得,Object(对象)最难.因为Javascript的Object模型很独特,和其他语言都不一样,初学者不容易掌握. 下面就是我的学习笔记,希望对大家学习这个部分有所帮助.我主要参考了以下两本书籍: <面向对象的Javascript>(Object-Oriented JavaScript) <Javascript高级程序设计(第二版)>

《JavaScript面向对象编程指南》——1.6 OOP概述

1.6 OOP概述 JavaScript面向对象编程指南 如果您在面向对象程序设计方面是一个新手,或者您不能确定自己是否真的理解了上面这些概念,请不必太担心.以后我们还会通过一些代码来为您具体分析它们.尽管这些概念说起来好像很复杂.很高级,但一旦进入真正的实践,事情往往就要简单得多. 话虽如此,但还是先让我们再来复习一下这些概念吧(见表1-1).

Javascript面向对象编程(二):构造函数的继承

Javascript面向对象编程(二):构造函数的继承 作者: 阮一峰 日期: 2010年5月23日 这个系列的第一部分,主要介绍了如何"封装"数据和方法,以及如何从原型对象生成实例. 今天要介绍的是,对象之间的"继承"的五种方法. 比如,现在有一个"动物"对象的构造函数. function Animal(){ this.species = "动物"; } 还有一个"猫"对象的构造函数. function

JavaScript 面向对象编程(2) 定义类_js面向对象

本文承接上一篇JavaScript面向对象编程(1) 基础. 上篇说过,JavaScript没有类的概念,需要通过函数来实现类的定义.先通过一个例子说明: 复制代码 代码如下: function myClass() { var id = 1; var name = "johnson"; //properties this.ID = id; this.Name = name; //method this.showMessage = function() { alert("ID:

JavaScript面向对象编程入门教程_基础知识

尽管面向对象JavaScript与其他语言相比之下存在差异,并由此引发了一些争论,但毋庸置疑,JavaScript具有强大的面向对象编程能力 本文先从介绍面向对象编程开始,然后回顾JavaScript对象模型,最后演示JavaScript中的面向对象编程概念. JavaScript回顾 如果你对诸如变量(variables).类型(types).函数(functions).以及作用域(scope)等JavaScript概念觉得心里没底,那么你可以阅读重新介绍JavaScript中的这些主题.你还

Javascript面向对象编程(三):非构造函数的继承

Javascript面向对象编程(三):非构造函数的继承 作者: 阮一峰 日期: 2010年5月24日 这个系列的第一部分介绍了"封装",第二部分介绍了使用构造函数实现"继承". 今天是最后一个部分,介绍不使用构造函数实现"继承". 一.什么是"非构造函数"的继承? 比如,现在有一个对象,叫做"中国人". var Chinese = { nation:'中国' }; 还有一个对象,叫做"医生&qu