JavaScript 中的面向对象编程详解

阅读时长 8 分钟读完

面向对象编程(Object-Oriented Programming,简称 OOP)是一种编程范式,它将数据和方法封装在一起,以类(class)和对象(object)为基础,通过对类的定义和对象的实例化来实现程序的设计。

JavaScript 具有面向对象的特性,但相对于其他语言,它的实现有所不同。在 JavaScript 中,我们可以通过函数来实现类的定义,通过对象字面量来实现对象的实例化,从而完成面向对象编程。

本文将详细介绍 JavaScript 中的面向对象编程,包括类、对象、构造函数、继承等内容,并提供示例代码以便读者理解和实践。

类和对象的定义

在 JavaScript 中,类可以通过函数来实现。我们定义一个函数,然后通过 new 关键字来实例化该函数即可创建一个对象。例如:

上面代码中,我们定义了一个叫做 Person 的函数,它有两个参数 nameage,并将它们添加到新创建的对象中。通过 new 关键字,我们分别创建了 person1person2 两个对象。

要注意的是,在 JavaScript 中,Object 类型是所有对象类型的基础。因此,我们可以通过 Object.create() 方法来创建一个对象,然后通过 Object.setPrototypeOf() 方法来设置该对象的原型(即它所继承的对象)。例如:

上面代码中,我们创建了一个没有原型的空对象 person3,然后通过 Object.setPrototypeOf() 方法将其原型设置为 Person 函数,最后给 person3 对象添加了两个属性 nameage

构造函数

上面我们使用函数来定义类,但是这些函数并不是专门为了创建对象而设计的,因此我们需要借助 JavaScript 中的构造函数来完成类的定义。

一个构造函数是一个普通的函数,但是其名称以大写字母开头,其内部使用 this 关键字来指向将被创建的对象,而不是返回一个值。例如:

上面代码中,我们将 Person 函数作为构造函数来创建了一个对象 person4

对象的属性和方法

通过构造函数创建的对象可以拥有其自己的属性和方法。

对象属性

对象的属性可以是普通的值类型,也可以是对象类型。我们可以通过 .[ ] 操作符来访问对象的属性,例如:

-- -------------------- ---- -------
-------- ------------ ---- -
  --------- - -----
  -------- - ----
  --------- - -
    ------ -------------------
    ------ ------------
  --
-

----- ------- - --- ------------- ----
-------------------------- -- -----
-------------------------------- -- ------------------

上面代码中,我们在 Person 构造函数内部定义了一个 info 对象属性,它包含了 emailphone 两个子属性。我们可以通过 person5.info.email 来获取 person5 对象中 info 属性下的 email 值。

对象方法

对象可以拥有其自己的方法,它们可以通过属性赋值表达式来定义。例如:

-- -------------------- ---- -------
-------- ------------ ---- -
  --------- - -----
  -------- - ----
  ------------ - ---------- -
    ------ ------ ------------- ---- -------------
  --
-

----- ------- - --- -------------- ----
------------------------------- -- ------ ----- ---- ---

上面代码中,我们在 Person 构造函数内部定义了一个 getInfo() 方法,它返回了一个字符串,包含了 person6 对象的 nameage 属性。

面向对象编程中的继承

继承是面向对象编程中常见的技术之一,它可以简化代码、提高代码复用性,减少出错率。

在 JavaScript 中,我们可以使用原型继承来实现继承。原型继承是指一个对象可以继承另一个对象的属性和方法,我们只需要设置一个对象作为另一个对象的原型对象即可实现继承。

原型链继承

使用原型链继承是一种最基本的继承方式,它通过将子类的原型对象指向父类的实例来实现继承。

-- -------------------- ---- -------
-------- ------------ ---- -
  --------- - -----
  -------- - ----
-

------------------------ - ---------- -
  ------ ------ ------------- ---- -------------
--

-------- ------------- ---- -------- -
  ----------------- ----- -----
  ------------ - --------
-

----------------- - --------------------------------
----------------------------- - --------
---------------------------- - ---------- -
  ------ --------- -----------------
--

----- -------- - --- --------------- --- --------
-------------------------------- -- ------ ----- ---- ---
----------------------------------- -- --------- -----

上面代码中,我们使用 Person 函数定义了一个父类,并将其 getInfo() 方法添加到了 Person.prototype 原型对象上。使用 Teacher 函数定义了一个子类,并在其中调用了父类的构造函数 Person.call(this, name, age) 来设置子类的属性,然后将 Teacher.prototype 原型对象设置为 Object.create(Person.prototype),即 Teacher 类的原型对象继承自 Person 类的原型对象。最后定义了一个 getSubject() 方法,用于获取 Teacher 类独有的属性 subject,并将其添加到了 Teacher.prototype 原型对象上。

组合继承

组合继承是指将原型链继承和构造函数继承两种方式结合起来的继承方式。其主要思想是在子类中调用父类的构造函数来设置子类的属性,然后将子类的原型对象设置为父类的原型对象。

-- -------------------- ---- -------
-------- ------------ ---- -
  --------- - -----
  -------- - ----
-

------------------------ - ---------- -
  ------ ------ ------------- ---- -------------
--

-------- ------------- ---- -------- -
  ----------------- ----- -----
  ------------ - --------
-

----------------- - --- ---------
----------------------------- - --------
---------------------------- - ---------- -
  ------ --------- -----------------
--

----- -------- - --- --------------- --- -----------
-------------------------------- -- ------ ----- ---- ---
----------------------------------- -- --------- --------

上面代码中,我们实现了与原型链继承相同的继承方式,但是我们使用了 Person.prototype 来设置 Teacher 类的原型对象,因此我们需要在调用 Teacher 函数之前先将 Teacher.prototype 的原型对象设置为 Person.prototype,以便子类可以继承父类的方法。

总结

本文详细介绍了 JavaScript 中的面向对象编程,包括类、对象、构造函数、继承等内容,并提供了示例代码供读者学习和实践。希望读者通过本文的介绍和实践,更深入地了解面向对象编程的思想和技术,从而提升自己的编程能力。

来源:JavaScript中文网 ,转载请注明来源 https://www.javascriptcn.com/post/64e5bf98f6b2d6eab3135692

纠错
反馈