首先创建构造一个新的构造函数,用于创建一类对象:
1 | //创建Person构造函数 |
以上这种形式,由于是在这个构造函数内部添加的sayName方法,所以构造函数每执行一次就会创建一个新的sayName方法,且每个实例的sayName方法都是唯一的:
1 | //调用方法 |
虽然两个方法都是唯一的,但功能一样而我们只需要一个,因此这是是完全没有必要的。
然后是第二种方法创建形式:
1 | //创建Person构造函数 |
第二种方式是在全局变量中定义,之后调用构造函数创建新的对象,每个对象的sayName方法都是全局作用域中定义的这个方法:
1 | //通过构造函数Person创建对象 |
虽然这个方式解决了sayName方法重复创建的问题,但同时也因为将方法定义在全局作用域中而污染了全局作用域的命名空间,若是之后新的函数命名与这个sayName方法重复将直接覆盖这个sayName方法,存在风险。
因此可以尝试第三种方式,由同一个构造函数创建的对象属于同一类对象,这些对象都带有一个隐含属性 __ proto__ ,其属性值保存着指向同一个原型的地址;即每个对象都有其原型,且同类对象共用一个原型;因此,可以将多个对象重复使用的属性或方法写入原型,既不会重复创建方法,也不会污染命名空间:
1 | //创建Person构造函数 |
每创建一个函数,解析器都会向该函数中添加一个属性-prototype,prototype属性对应着一个对象,这个对象就是原型对象,通过prototype属性就能将方法或属性写入原型对象中
1 | //通过构造函数Person创建对象 |
这时创建的对象由于共用原型对象,而方法写在原型对象中,因此它们访问的是同一个sayName方法,解决了产生的问题。