javascript进阶

创建对象

工厂模式

通过创建函数调用函数来创建对象

function createBottle(name,price,isKeepWarm){
  return{
    name: name,
    price: price,
    isKeepWarm: isKeepWarm
  };
}
var bottle = createBottle('太空杯',49,false);
var bottle2 = createBottle('bottle',49,true);
var bottle3 = createBottle('bottle',59,true);

函数

属性:name\length\prototype
方法:bind()\call()\apply()
arguments\this

函数的arguments

function createBottle(name,price,isKeepWarm){
      return{
        name: name,
        price: price,
        isKeepWarm: isKeepWarm
      };
    }

可以写成

function createBottle(){
      return{
        name: arguments[0],
        price: arguments[1],
        isKeepWarm: arguments[2]
      };
    }
  • 是个对象,类数组,length属性
  • 不要滥用,会影响程序的可读性
  • 非常适合动态函数的场景

函数的this

执行环境
看作用域,作用域不同,this所代表的值也不同。

函数的方法

  • bind()
    改变函数的this指向
  • call()
    改变函数的this,传参可以直接传
  • apply()
    改变函数的this,传参以数组的形式

函数的属性

  • name
  • length
    声明的时候确定的参数length
    • arguments.length
      调用的时候传入的参数length
  • prototype
    对象,实现继承的重要属性

函数是first class

数据类型
First Class 可以作为函数的参数和返回值,也可以赋给变量
Second Class 可以作为函数的参数,但不能从函数返回,也不能赋给变量
Third Class 不能作为函数的参数

var add = function(a,b){
  return a + b;
};
var add = new Function('a','b','return a + b;');

闭包

闭包是指有权访问另一个函数作用域中的变量的函数

function foo(){
	var a = 'test';
	function bar(){
		return a;
	}
	retrun bar;
}
var bar = foo();
bar();

私有变量和特权方法

私有变量:

  • 任何在函数中定义的变量,都可以认为是私有变量。因为不能在函数外部访问这些变量。
  • 私有变量包括函数参数,局部变量以及在函数内部定义的其他函数。

特权方法:

有权访问私有变量和私有函数的公有方法
在函数的内部创建一个闭包,那么闭包通过自己的作用域链也可以访问这些私有变量

构造函数

instanceof 是实例

var bottle = new Bottle(‘杯子’,59,true);
console.log(bottle instanceof Bottle);

构造函数:

  • 没有显示的创建对象
  • 将属性和方法赋值给this
  • 没有return语句

(使用new)

构造函数的不足之处
功能相同的函数,重复声明消耗空间

原型prototype

原型是函数的一个属性,是一个对象
如果函数作为构造函数使用,那么这个构造函数的所有实例,都共享这个原型对象

  • constructor
    指向构造函数
  • 读写
    解决构造函数的浪费内存问题
  • isPrototypeOf
    检测实例是不是挂了原型

共享的缺陷

数据污染

完美地创建对象--构造函数结合原型

1.构造函数独享属性
2.原型共享方法

  • 属性的覆盖
    实例属性会覆盖原型中的属性
  • 属性的判断
    • in操作符
      判断对象里有没有某个属性
    • hasOwnProperty
      判断属性是挂在实例上而不是原型上

继承

原型链

  • 打通原型链
    Children.prototype = new Parents();

PS:原型链的不足

  1. constructor 指向问题
    手动指向原型链
    Children.prototype = new Parents();
    Children.prototype.constructor = Children;

  2. 属性共享问题
    数据污染

  3. 参数
    参数固定,不能传递参数

借用构造函数继承

function Parents(color){
    this.color = color;
}
function Children(color){
    Parents.call(this,color);
}

组合继承

  1. 属性和方法都是从父类继承的(代码复用)
  2. 继承的属性是私有的(互不影响)
  3. 继承的方法都在原型里(函数复用)

PS:组合继承的不足

1.重复调用,浪费

2.属性冗余

最佳实践

inheritPrototype(subType,superType){
    var protoType = Object.create(superType.prototype);//复制父类的原型
    protoType.constructor = subType;//重置constructor
    subType.prototype = protoType;//修改子类原型
}

继承属性
继承方法

ES6创建类用class
ES6继承通过extends

class Student extends Person {
    // 构造函数
    constructor(name, grade) {
        super(name);
        this.grade = grade;
    }

    // 方法
    sayGrade() {
        console.log(`I am Grade ${this.grade}`);
    }
}

p(HTMLParagraphElement)\div(HTMLDivElement)\input(HTMLInputElement)
---------继承自---------->HTMLElement
---------继承自---------->Element
---------继承自---------->Node

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值