简单理解js的prototype属性及使用


Posted in Javascript onDecember 07, 2016

在进入正文之前,我得先说说我认识js的prototype这个东西的曲折过程。

百度js的prototype的文章,先看看,W3School关于prototype的介绍:

简单理解js的prototype属性及使用

你觉得这概念适合定义js的prototype这个东西吗?你是否也认为prototype是一个object对象的属性呢?是的话,请认真认真看我这篇文章,因为这篇文章会毁灭你的人生三观,呵呵,就是有这么严重,因为本人就是被这个定义给害惨的。

不得不说,看了网上的一些介绍prototype的文章,基本上都说prototype是对象的一个属性,于是,我也坚定的认为prototype是一个对象的属性,所以,我被了坑好久好久,由此,引发的后果就是,我一次次的误解别人写的含有prototype的js代码,也就是当别人亮出js的prototype这个属性来写js代码时,我看着他们写的代码都是 ····一头雾水·····

,悲催啊!所以,我恨死prototype这个东西了,因此,在这里,我今天必须把js的prototype属性道个明明白白。看官,请擦亮你的眼睛,仔细看我下面的实验。

当然,我希望诸位看官也能够静下心来,把我下面的实验重新做一遍,好证明我的结论是正确的。

同时,也为了证明·····我没有····骗你们·····,呵呵,废话不多说了,下面进入实验阶段。

先介绍一个下面要用到的函数,JSON.stringify(value)。

这个函数的作用是:把传入的参数value变成字符串,它有三个参数,第一个参数是必须的,其余的两个参数可填可不填。

关于JSON.stringify函数的作用请看这篇文章。https://3water.com/article/29893.htm,这里说的很清楚。

首先,测试W3Schol的定义到底行不行的通:

如果,真如W3Schol所说的那样,prototype是object的一个属性,那么,我们来创建一个对象,看看这个对象的prototype到底是啥。

var ob = { };//超级简单的空对象
alert(JSON.stringify(ob.prototype));

你觉得上面的代码会alert出什么呢?既然prototype是object的一个属性,那么上面肯定能够获取到什么东西对吧?但是,如果你拿这段代码去做实验了,你会被打脸的,因为它alert的东西是·········undefined··········,也就是说object这个属性prototype不是个东西,很残酷吧,但现实就是这样,任何对象引用prototype都会出现undefined,不信,你可以试一试。

我可以很明白的告诉你,prototype绝对不是给对象用的,对象根本没办法引用prototype这个属性,它真正的属主,其实是···········函数········,记住,能够引用prototype的东西绝对是函数,绝对是函数,绝对是函数,prototype是属于函数的一个属性,prototype是属于函数的一个属性,prototype是属于函数的一个属性,能够引用它的只有·····函数····,能够引用它的只有·····函数·····,能够引用它的只有····函数····,函数,函数,函数,重要的事情一定要说千百遍,呵呵,因为只有明确这一点,下面,你才明白我要讲的东西。别怪我这么墨迹啊!

下面,我要给prototype一个名副其实的定义:

prototype是函数的一个属性,是函数的原型对象。

就是这么简单,能看明白吗? prototype只能够被   函数     调用

别搞混了js的object对象和function函数,js的对象和函数绝对是两个概念,为什么?因为js的function函数可以new出object对象啊,是吧?这个你总该知道吧?

下面,来做试验证明我的结论。

 

//首先定义一个有名函数func
function func(){
  
}
alert(func.prototype);

你说,上面的代码会alert什么呢?还会不会是undefined的呢?我敢肯定的告诉你绝对不是undefined的,因为本人已经alert过了,呵呵。

上面,弹出的窗口是:

简单理解js的prototype属性及使用 

没错,返回的就是对象,这回你肯相信我,能够调用prototype的一定是函数了吧?object引用prototype的时候给你返回的是一个不是东西的东西undefined,函数引用prototype的时候给你返回一个真真实实存在的东西object的,这还不够证明prototype是给函数用的吗?还不能够证明对象是不能引用prototype的吗?呵呵,又多说了。

上面我已经说过,prototype是函数的一个属性,也是函数的原型对象,而这里func函数引用prototype的时候返回的是一个对象object的,那么,结合这两个概念,你能得出什么结论呢?我想通过这不难得出结论:

prototype是········函数的原型对象············,这能理解吗?不能理解,没有关系,我们再来做一个实验,终于要用到文章开始给你们介绍的一个函数JSON.stringify()了。

function func(){
  
}
alert(JSON.stringify(func.prototype));

还是引用上面的函数func,只不过这里返回的是JSON.stringify()函数的返回值。

简单理解js的prototype属性及使用

你没有看错,这里alert的结果是一个空对象,这证明,prototype的的确确属于函数的属性,并且函数的prototype属性的js数据类型是对象,明白不?为什么现在是一个空对象?你有没有想过?为什么呢?请思考这个问题三秒钟,假如想不出来,那么没有关系,下面,我来解释。

先看,实验代码:

function func(){
  
}
func.prototype.name ='prototype是函数的的属性,本质是函数的原型对象';
alert(JSON.stringify(func.prototype))

你说,上面的代码会alert出什么呢?请看下面:

简单理解js的prototype属性及使用

你没有看错,此刻,终于alert出东西来了,我在这里给prototype赋于一个属性name,所以,我这个时候在alert函数func的prototype时,你看到有值了吗?看到了prototype的属性name值了吗?现在再想想,为什么上面第一层alert函数func.prototype的时候,它是一个空对象呢?而现在它又是一个有值的对象呢?

原因很简单呢,因为第一次的时候,我没有给函数的属性func.prototype赋予name属性,也没有给name属性赋值啊,而现在我已经给函数的属性func.prototype赋予属性name,并且赋值为········prototype是函数的的属性,本质是函数的原型对象······,所以,现在alert函数的属性func.prototype的时候它就有值啦,对吧?

因此,这里得出结论:

prototype是函数的的属性,本质是函数的原型对象。

别以为js中只有对象才有属性,通过这里,我们也可以知道,其实js的函数也是有属性的,而且js的函数好像就只有这个属性prototype,而且js的这个函数属性同时还是函数的原型对象,你是不是被搞晕了?希望你没有被搞晕才好。

为什么说prototype是函数的一个属性呢?因为,只有函数才能调用prototype,而且是以这样的方式func.prototype调用的,这样的方式调用东西是不是和对象调用属性一模一样呢?是的,就是因为函数调用prototype的时候是和对象调用属性的时候一样的,我们才把prototype说成是函数的一个属性,而函数的这个属性其实是一个对象(这个是不是对象,上面已经证明了,这里就不再说明),所以说,这个prototype就是函数的属性,本质是函数的原型对象。

这里为什么强调说prototype的本质是函数的原型对象呢?

下面看代码证明,我的代码很简单的:

//定义一个函数
  function func(){
  
  }
  //给函数的属性prototype赋予一个方法get
  func.prototype.get=function(value){
    return value;//很简单,你给我什么我就输出什么
  }

你说,怎么调用上面那个get方法?

我给你一点提示,get是属于func函数的一个属性函数,既然是属性函数,那么我们怎么调用呢?

很简单,属性函数必须由它的对象来调用,那么我们怎么获取get的对象呢?很简单,用关键字new来实例化func函数的对象就行了吗?是吧?

下面,实例化func函数的一个对象ob1:

var ob1 = new func();
//用func实例化出来的对象来调用get属性函数
alert(ob1.get('hello,prototype原型对象'));

简单理解js的prototype属性及使用

没错,用func函数实例化出来的对象ob1,确实能够调用get函数,上面已经利用ob1调用get函数alert出来了,这就证明func函数的实例对象是拥有get这个属性函数的,对吧?这么明显,就不用说明了吧。

如果,你不信必须要用实例化func的对象来调用get函数,你可以试试直接用func调用get函数,也就是说,你可以尝试着func.get()调用一下get函数看看,看func它到底能不能够直接调用get函数。我想一定报错,呵呵,原因是什么,你自己想。

那么,说了这么多,我还是没有说明,为什么我说prototype的本质是函数的原型对象啊?对吧?

请看,下面的代码:

var ob2 = new func();
//用func实例化出来的对象来调用get属性方法
alert(ob2.get('我依然是func实例化出来的对象'));

简单理解js的prototype属性及使用

看到没有,我还是再次利用func函数实例化一个ob2,这个对象依然能够调用get属性函数,这说明什么了呢?这说明了,利用func对象实例化的所有对象都可以调用get这个属性函数。既然如此,你说,prototype这个属性如果不是函数func的原型对象的话,那么为什么给prototype赋予的属性函数get能够被func所有实例化的对象所调用呢?假如prototype的本质不是func函数的原型对象,那么依据func函数实例化出来的对象就不可能一个个都能够调用get这个属性方法,对吧?为什么?我们来个比例,你说,一个不是源头的东西,它能影响到所有的东西吗?不能够吧?因此,这里得出结论:

prototype是函数的一个属性,本质就是函数的原型对象。

整篇文章就是为了说明这个结论。无他。希望看官能看懂这篇文章。对于prototype的应用下篇文章再讲,在此打住。

特别指出:

  • Array.prototype是一个数组
  • String.prototype是一个字符串
  • Object.prototype是一个对象

这三个特殊例子,不像构造函数的prototype一样,当然,假如你真的理解prototype是函数的一个原型对象的话,你应该知道,数组的原型对象应该是一个数组,而不可能是一个对象吧?字符串的原型对象应该是字符串而不可能是对象吧?详情请看下一篇文章。

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
仿迅雷焦点广告效果(JQuery版)
Nov 19 Javascript
JavaScript传递变量: 值传递?引用传递?
Feb 22 Javascript
创建公共调用 jQuery Ajax 带返回值
Aug 01 Javascript
javascript原型继承工作原理和实例详解
Apr 07 Javascript
第一篇初识bootstrap
Jun 21 Javascript
AngularJS动态绑定HTML的方法分析
Nov 07 Javascript
用Vue-cli搭建的项目中引入css报错的原因分析
Jul 20 Javascript
Webpack性能优化 DLL 用法详解
Aug 10 Javascript
Express的HTTP重定向到HTTPS的方法
Jun 06 Javascript
如何解决js函数防抖、节流出现的问题
Jun 17 Javascript
Vue脚手架编写试卷页面功能
Mar 17 Javascript
vue 如何从单页应用改造成多页应用
Oct 23 Javascript
Bootstrap基本组件学习笔记之列表组(11)
Dec 07 #Javascript
Bootstrap基本样式学习笔记之图片(6)
Dec 07 #Javascript
JavaScript学习笔记--常用的互动方法
Dec 07 #Javascript
详解JavaScript的内置对象
Dec 07 #Javascript
Bootstrap基本样式学习笔记之标签(5)
Dec 07 #Javascript
Bootstrap基本样式学习笔记之按钮(4)
Dec 07 #Javascript
jQuery中get方法用法分析
Dec 07 #Javascript
You might like
phpMyAdmin出现无法载入 mcrypt 扩展,请检查PHP配置的解决方法
2012/03/26 PHP
浅谈PHP正则表达式中修饰符/i, /is, /s, /isU
2014/10/21 PHP
CI框架验证码CAPTCHA辅助函数用法实例
2014/11/05 PHP
制作安全性高的PHP网站的几个实用要点
2014/12/30 PHP
纯js实现的论坛常用的运行代码的效果
2008/07/15 Javascript
基于jquery的从一个页面跳转到另一个页面的指定位置的实现代码(带平滑移动的效果)
2011/05/24 Javascript
jQuery.event兼容各浏览器的event详细解析
2013/12/18 Javascript
通过JS来动态的修改url,实现对url的增删查改
2014/09/01 Javascript
jQuery简单实现网页选项卡特效
2014/11/24 Javascript
封装好的js判断操作系统与浏览器代码分享
2015/01/09 Javascript
JQuery勾选指定name的复选框集合并显示的方法
2015/05/18 Javascript
微信WeixinJSBridge API使用实例
2015/05/25 Javascript
jQuery的ajax和遍历数组json实例代码
2016/08/01 Javascript
详解angularjs中如何实现控制器和指令之间交互
2017/05/31 Javascript
Vue列表页渲染优化详解
2017/07/24 Javascript
从零开始封装自己的自定义Vue组件
2018/10/09 Javascript
ant-design-vue中tree增删改的操作方法
2020/11/03 Javascript
Django中更改默认数据库为mysql的方法示例
2018/12/05 Python
python实现大文件分割与合并
2019/07/22 Python
python+tkinter实现学生管理系统
2019/08/20 Python
python读取Excel表格文件的方法
2019/09/02 Python
Python:type、object、class与内置类型实例
2019/12/25 Python
Python selenium爬取微信公众号文章代码详解
2020/08/12 Python
Python3中小括号()、中括号[]、花括号{}的区别详解
2020/11/15 Python
Python获取指定网段正在使用的IP
2020/12/14 Python
Python制作运行进度条的实现效果(代码运行不无聊)
2021/02/24 Python
一文读懂python Scrapy爬虫框架
2021/02/24 Python
html5 canvas合成海报所遇问题及解决方案总结
2017/08/03 HTML / CSS
库存图片、照片、矢量图、视频和音乐:Shutterstock
2021/02/12 全球购物
Java里面如何把一个Array数组转换成Collection, List
2013/07/26 面试题
霸王洗发水广告词
2014/03/14 职场文书
大学生思想道德自我评价
2015/03/09 职场文书
限期整改通知书
2015/04/22 职场文书
开业庆典致辞
2015/08/01 职场文书
MongoDB日志切割的三种方式总结
2021/09/15 MongoDB
nginx搭建NFS网络文件系统
2022/04/14 Servers