JavaScript 中的构造函数与原型:有什么区别?

本文探讨JavaScript中的构造函数与原型的区别。构造函数用于创建对象,而原型是对象间共享属性和方法的机制,通过原型链实现。文章通过示例说明两者在对象创建和方法共享上的差异,强调了在创建对象后可以修改原型添加新属性和方法。最后,作者分享了一份关于JavaScript与ES的笔记供读者学习。

当您在学习 JavaScript 时,可能会混淆构造函数原型之间的区别。通常,它们可以互换使用来描述相似的概念,但它们实际上是用于不同目的的不同事物。

在这篇文章中,我们将揭开这两个术语的神秘面纱并解释它们之间的区别。

简单的区分

那么构造函数和原型有什么区别呢?

一个简单的区分是,构造函数是一个用于创建对象的函数,而原型是一个包含属性和方法的对象,这些属性和方法由从构造函数创建的对象继承。

我们来看一个例子:

function Person(name) {this.name = name;
}

Person.prototype.sayHello = function() {console.log(`Hello, my name is ${this.name}.`);
}

const person = new Person('John');

person.sayHello(); // Hello, my name is John. 

在上面的示例中,我们有一个构造函数,它接受一个name参数并将其分配给name对象的属性。我们还有一个名为 sayHello的原型方法,它向控制台打印一条消息。

当我们Person使用构造函数创建一个新对象时,我们可以调用它的sayHello方法,它会打印带有我们传递给构造函数的名称的消息。

person对象可以使用该方法sayHello,因为它继承自 Person构造函数的原型。

系统的区分

构造函数概述

构造函数是用于创建对象的函数。当您使用关键字调用构造函数时new,它将创建一个新对象并返回它。

如果您有面向对象编程(OOP)的 背景,将构造函数与类进行比较是最简单的。就像在其他语言中一样,构造函数允许您创建新对象并定义它们的属性和方法。

例如,让我们比较一个简单的 Java 类,以及我们如何使用构造函数在 JavaScript 中实现相同的功能:

Java

public class Person {private String name;public Person(String name) {this.name = name;}public void sayHello() {System.out.println("Hello, my name is " + this.name);}
}

Person person = new Person("John");
person.sayHello(); // Hello, my name is John 

JavaScript

在 JavaScript 中,我们可以创建Person具有相同属性和方法的构造函数:

function Person(name) { this.name = name; 
}Person.prototype.sayHello = function() { console.log(`Hello, my name is ${this.name}.`);
}const person = new Person('John'); 
person.sayHello(); // Hello, my name is John. 

如您所见,两者非常相似。主要区别在于,在 JavaScript 中,我们使用prototype将方法添加到构造函数中,而在 Java 中,我们只需将它们添加到类中。

事实上,ES6 附带的新类语法是语法糖,旨在使构造函数的使用更类似于其他 OOP 语言。

还要注意我们如何this 在 JavaScript 构造函数中使用。this指使用new关键字时隐式创建的对象。

原型概述

现在让我们更详细地介绍一下原型,以及为什么我们使用它在创建的对象之间共享构造函数的属性和方法。

在 JavaScript 中,函数本身也是 JS 对象,它们有一个叫做原型的属性。

原型的目的是在从构造函数创建的对象之间共享属性和方法。

例如,在上面的 Person 构造函数中,我们向sayHello原型添加了一个方法。这意味着从 Person 构造函数创建的每个对象都有一个sayHello方法。

原型链

Prototype 以一种节省内存的方式在对象之间共享属性。如果我们向原型添加一个方法,则该方法的一个实例只存在于内存中,并且在从构造函数创建的所有对象之间共享。

如果我们将sayHello方法直接添加到 Person 构造函数中,那么每个对象都将拥有该方法的自己的副本,从而占用更多内存。

这称为原型链,它是 JavaScript 语言的重要组成部分。

下面是原型链的工作原理: 当 JavaScript 在对象上查找属性时,它会首先检查该属性是否存在于对象本身上。如果没有找到,它会查看对象的原型,看属性是否存在。

如果不存在,它将查看原型的原型,依此类推,直到找到匹配项或到达原型链的末尾。

创建对象后修改原型

使用构造函数和原型的好处之一是我们可以在创建对象后向原型添加新的属性和方法。

例如,假设我们要向Person 构造函数添加一个getName方法:

function Person(name) { this.name = name;
}
Person.prototype.sayHello = function() {console.log(`Hello, my name is ${this.name}.`);
}const person = new Person('John');person.sayHello(); // Hello, my name is John 

Person.prototype.getName = function() {return this.name; 
}
console.log(person.getName()); // John 

如您所见,我们能够在创建对象getName后将方法添加到原型person中,并且仍然可以按预期工作。

结论

总之,JavaScript中构造函数和原型的主要区别在于构造函数用于创建对象,而原型用于在对象之间共享属性和方法。

最后

最近还整理一份JavaScript与ES的笔记,一共25个重要的知识点,对每个知识点都进行了讲解和分析。能帮你快速掌握JavaScript与ES的相关知识,提升工作效率。



有需要的小伙伴,可以点击下方卡片领取,无偿分享

评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值