js进阶二(applycallbind闭包函数也是对象概念)
Posted 易辰_
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了js进阶二(applycallbind闭包函数也是对象概念)相关的知识,希望对你有一定的参考价值。
文章目录
apply\\call
apply和call可以改变this的指向
function f1(x, y)
console.log("结果是:" + (x + y) + this);
return "10000";
f1(10, 20);//函数的调用
window.f1(10, 20);
var r1 = f1.apply(null, [1, 2]);//此时f1中的this是window
console.log(r1);
var r2 = f1.call(null, 1, 2);//此时f1中的this是window
console.log(r2);
var obj =
age: 10,
sex: "男"
;
window.f1.apply(obj, [10, 20]);
window.f1.call(obj, 10, 20);
输出如下:
结果是:30[object Window]
结果是:30[object Window]
结果是:3[object Window]
10000
结果是:3[object Window]
10000
结果是:30[object Object]
结果是:30[object Object]
我们在来看一个例子
function Person(age,sex)
this.age=age;
this.sex=sex;
//通过原型添加方法
Person.prototype.sayHi=function (x,y)
console.log("您好啊:"+this.sex);
return 1000;
;
var per=new Person(10,"男");
per.sayHi();
console.log("==============");
function Student(name,sex)
this.name=name;
this.sex=sex;
var stu=new Student("小明","人妖");
var r1=per.sayHi.apply(stu,[10,20]);
var r2=per.sayHi.call(stu,10,20);
console.log(r1);
console.log(r2);
输出如下:
您好啊:男
==============
您好啊:人妖
您好啊:人妖
1000
1000
函数也是对象
function f1()
console.log(this+":====>调用了");
//f1是函数,f1也是对象
console.dir(f1);
//对象调用方法,说明,该对象中有这个方法
f1.apply();
f1.call();
console.log(f1.__proto__==Function.prototype);
输出如下:
ƒ f1()
[object Window]:====>调用了
[object Window]:====>调用了
true
bind
复制了一份的时候,把参数传入到了f1函数中,x===>10,y===>20,null就是this,默认就是window
bind方法是复制的意思,参数可以在复制的时候传进去,也可以在复制之后调用的时候传入进去
apply和call是调用的时候改变this指向
bind方法,是赋值一份的时候,改变了this的指向
function f1(x, y)
console.log((x + y) + ":=====>" + this.age,this);
var ff = f1.bind(null);
ff(10, 20);
//person对象
function Person()
this.age = 1000;
Person.prototype.eat = function ()
console.log("这个是吃");
;
var per = new Person();
//传递person实例对象
var ff = f1.bind(per, 10, 20);
ff();
结果输出如下:
30:=====>undefined Window postMessage: ƒ, blur: ƒ, focus: ƒ, close: ƒ, frames: Window, …
30:=====>1000 Person age: 1000
匿名函数返回值
function File(name, size, time)
this.name = name;//电影名字
this.size = size;//电影大小
this.time = time;//电影的上映时间
var f1 = new File("jack.avi", "400M", "1997-12-12");
var f2 = new File("tom.avi", "200M", "2017-12-12");
var f3 = new File("xiaosu.avi", "800M", "2010-12-12");
var f4 = new File("xiaosu.bvi", "800M", "2010-12-12");
var arr = [f3,f4,f1, f2, ];
function fn(attr)
//函数作为返回值
return function getSort(obj1, obj2)
if (obj1[attr] > obj2[attr])
return 1;
else if (obj1[attr] == obj2[attr])
return 0;
else
return -1;
var ff = fn("name");
//函数作为参数
arr.sort(ff);
for (var i = 0; i < arr.length; i++)
console.log(arr[i].name + "====>" + arr[i].size + "===>" + arr[i].time);
输出如下:
jack.avi====>400M===>1997-12-12
tom.avi====>200M===>2017-12-12
xiaosu.avi====>800M===>2010-12-12
xiaosu.bvi====>800M===>2010-12-12
闭包
闭包可以缓存数据
//普通的函数
function f1()
var num = 10;
num++;
return num;
console.log(f1());
console.log(f1());
console.log(f1());
//函数模式的闭包
function f2()
var num = 10;
return function ()
num++;
return num;
var ff = f2();
console.log(ff());//11
console.log(ff());//12
console.log(ff());//13
输出如下:
11
11
11
11
12
13
我们来看另外一个例子
function count()
var arr = [];
for (var i=1; i<=3; i++)
arr.push(function ()
return i * i;
);
return arr;
var results = count();
var f1 = results[0];
var f2 = results[1];
var f3 = results[2];
console.info(f1())
console.info(f2())
console.info(f3())
输出均为16
原因就在于返回的函数引用了变量i,但它并非立刻执行。等到3个函数都返回时,它们所引用的变量i已经变成了4,因此最终结果为16。
返回闭包时牢记的一点就是:返回函数不要引用任何循环变量,或者后续会发生变化的变量。
function count()
var arr = [];
for (var i=1; i<=3; i++)
arr.push((function (n)
return function ()
return n * n;
)(i));
return arr;
var results = count();
var f1 = results[0];
var f2 = results[1];
var f3 = results[2];
console.info(f1())
console.info(f2())
console.info(f3())
输出1 4 9
闭包不仅可以为了返回一个函数然后延迟执行
在面向对象的程序设计语言里,比如Java和C++,要在对象内部封装一个私有变量,可以用private修饰一个成员变量。
在没有class机制,只有函数的语言里,借助闭包,同样可以封装一个私有变量。我们用javascript创建一个计数器:
function create_counter(initial)
var x = initial || 0;
return
inc: function ()
x += 1;
return x;
它用起来像这样:
var c1 = create_counter();
c1.inc(); // 1
c1.inc(); // 2
c1.inc(); // 3
var c2 = create_counter(10);
c2.inc(); // 11
c2.inc(); // 12
c2.inc(); // 13
在返回的对象中,实现了一个闭包,该闭包携带了局部变量x,并且,从外部代码根本无法访问到变量x。换句话说,闭包就是携带状态的函数,并且它的状态可以完全对外隐藏起来。
以上是关于js进阶二(applycallbind闭包函数也是对象概念)的主要内容,如果未能解决你的问题,请参考以下文章