zoukankan      html  css  js  c++  java
  • JavaScript原型(链)学习笔记

    javascript是基于原型的一门脚本语言,那究竟原型是什么?

    本文将从以下几个方面重点阐述原型

    1. 构造函数是什么?
    2. 构造函数和我们常见的Array String有什么关系?
    3. 原型的使用?
    4. __proto__是什么?
    5. constructor是什么?
    6. 什么是原形链?

    一:请看下面一段代码

    //声明一个构造函数 函数名首字母一般大写    
    function Fn() {
    	
    }
    
    Fn.prototype.a = function() {
         alert(1);
    }
    //得到实例化对象
    var f1 = new Fn();
    //调用构造函数的原型方法
    f1.a();
    

    上面这段代码执行后结果会弹出1,可能有小伙伴看不懂我为什么要在这里讲构造函数了。暂且不急,再看看下面这段代码。

    数组的使用

    var arr = [1,2,3];
    arr.push(4);
    

    如果细心的小伙伴可能看出来上面的代码和这两行代码有点像。不过肯定有些人觉得不像,那我继续转换一下。

    var arr = new Array(1,2,3);
    arr.push(4);
    

    数组也是构造函数?

    瞬间感觉到很熟悉 有木有,Array也是一个构造函数吗?
    下面我们来实践一下就知道了

    `alert(typeof Array) //function`
    

    原来javascript内置的这些方法也是用构造函数的方法实现的。
    比如Array.push 就是通过

    Array.prototype.push = function(){//代码实现}

    那是不是也意味着我们可以直接篡改这些原生方法?

    答案是肯定,在这里我就证明了。不过我不建议这样干,因为会造成代码混乱。

    我们只要通过new 一个函数,就可以实例化得到这个对象,可以直接在这个构造函数上面添加原型方法,实例化的对象就直接能使用这个对象了。
    下面再让大家看一张图和一段代码深入了解一下原型。

    function Fn() {
        //在构造函数中,this指向构造函数本身
        this.x = 1;
    }
    Fn.prototype.x = 2;
    var f1 = new Fn();
    f1.x = 3;
    console.log(f1.x);
    

    脑图!
    请问输出结果到底是?
    我们来分析一下这张图片。
    1、现在f1是通过Fn构造函数实例出的对象,从图中我们可以清楚看出f1.x 距离f1最近,那必然结果是3.
    2、假如现在注释掉f1.x = 3;,那答案又是多少? 我们只要又从图中找,
    f1距离Fn.x = 1;(图中写出Fn.a = 1了,作图的时候太马虎了).

    想必看到这里大家对于原形有了初步了解,那我再总结一下。
    通俗来讲,原型就是构造函数下面的方法和属性,重要的事情说三遍,为了区分普通函数,构造函数首字母大写。通过new这个构造函数,得到实例化对象。然后挂载在构造函数上面的方法和属性就可以直接用了。最常见就是Array,String这些常见属性和方法了。


    什么是__proto__?

    每个函数function都有一个prototype,即原型。这里再加一句话——每个对象都有一个__proto__,可成为隐式原型。

    console.log(f1.__protot__ === Fn.prototype) //true
    

    限于篇幅,在这里就不过多介绍这个属性了,感兴趣的朋友可以查阅相关资料。


    constructor是什么?

    再回到之前那张流程图,在Fn原型下有个constructor属性,那这个属性是怎么来的?有什么用呢?
    

    每个构造函数都会默认生成一个这个属性,它的作用是指向构造函数本身。
    可能有朋友看到过怎么判断一个变量是不是数组的面试题?
    如果用了这个constructor判断是不是指向Array就入了大坑了,因为我们可以手动修改这个constructor指向。
    最好使用
    Object.prototype.toString.call(arr) === '[object Array]';


    这个constructor到底怎么来的?

    为了目标这个问题,我们的得弄明白,引用类型和值类型。像String,Number,undefined,boolean类型,这些都是值类型,而引用类型是Object,function,null之类的。引用类型都是对象,对象是属性的集合。
    

    Object的原型下有个方法就是constructor,而我们创建的f1的constructor就是来源于Object,通过原形链的方法去查找。即Object是顶层对象,当我们要访问f1.constructor的时候,发现Fn构造函数上没有这个属性,那我们去创建Fn对象(Fn是一个构造函数,当然也是一个引用类型,那必须是对象啊)构造函数上去找,最后找到Object上去了。这就构成了原形链。真是环环相扣啊。


    注:限于知识水平不够,可能有些地方解释的不够清楚,本人也一直在学习当中!如果有错误,欢迎大家指正,共同学习!

  • 相关阅读:
    oracle 对应的JDBC驱动 版本
    Java Web中如何访问WEB-INF下的XML文件
    网站制作越简单越好(一):css样式命名规范
    HTTPClient以WebAPI方式发送formData数据上传文件
    NetCore(依赖注入)
    JS a标签 onClick问题
    NetCore的配置管理(1)
    Centos 系统安装NetCore SDK命令以及一系列操作(3)
    Centos 系统安装NetCore SDK命令以及一系列操作(2)
    Centos 系统安装NetCore SDK命令以及一系列操作(1)
  • 原文地址:https://www.cnblogs.com/Aralic/p/4466343.html
Copyright © 2011-2022 走看看