博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
第三天 函数
阅读量:7008 次
发布时间:2019-06-28

本文共 4506 字,大约阅读时间需要 15 分钟。

1、函数调用,方法调用及构造函数调用之间的不同

这部分比较简单,直接看代码吧:

function hello() {    console.log('Hello, World');}// 函数的调用hello(); // Hello, Worldvar obj = {    welcome: function() {        console.log('Hello, ' + this.name);    },    name: 'dreamapple'};// 方法调用obj.welcome(); // Hello, dreamapplefunction Student(name, age) {    this.name = name;    this.age = age;    console.log('My name is ' + this.name + ', and my age is ' + this.age);}// 构造函数的调用var s = new Student('dreamapple', 23); // My name is dreamapple, and my age is 23

注意

  • 函数调用将全局对象(处于严格模式下则为undefined)作为接收者。一般很少使用函数调用语法来调用方法。

  • 方法调用将被查找方法属性的对象作为调用接受者。

  • 构造函数需要通过new运算符调用,并产生一个新的对象作为其接受者。

2、掌握高阶函数的使用

JavaScript中将函数作为参数或返回值的函数被称为高阶函数,下面介绍一些常用的JS内置高阶函数

Array.sort

  • sort 函数需要使用者传入一个排序规则,如下:

var arr = [1, 9, 3, 4, 2];// 返回一个排序的结果var arr1 = arr.sort(function(x, y) {return x>y?1:-1});console.log(arr1); // [ 1, 2, 3, 4, 9 ]

Array.map

  • 使用 map 可以简化对数组的遍历操作,其参数为一个函数,如下:

var arr = [1, 9, 3, 4, 2];var arr2 = arr.map(function(x) {    return x * 2 + 1;});console.log(arr2); // [ 3, 5, 7, 9, 19 ]var arr3 = [1.4,1.5,3.2,3.6]arr3 = arr3.map(Math.ceil)console.log(arr3)//[2, 2, 4, 4]

call

  • 使用call方法自定义接受者来调用函数。

  • 使用call方法可以调用在给定的对象中不存在的方法。

  • 使用call方法定义高阶函数允许使用者给回掉函数指定接收者。

// 使用callvar obj1 = {    sayHello: function(msg) {        console.log('Hello,' + this.name + ' ' + msg);    },    name: 'dreamapple'};var obj2 = {    name: 'dream'};// 第一个参数是方法的调用者,剩余的参数就是原函数的参数obj1.sayHello.call(obj2, 'haha'); // Hello,dream haha// 高阶函数使用callfunction compute(arg) {    var sum = 0;    for(var i = 0; i < arg.length; i++) {        sum += arg[i];    }    return sum;}function highFunc() {    return compute.call(null, arguments);}console.log(highFunc(1, 2, 3, 4, 5)); // 15var arr = [1,2,3,4,5];console.log(highFunc(arr)); // 错误

arguments 的使用

JavaScript给每个函数都隐式地提供了一个局部变量 arguments

  • 使用隐式的arguments对象实现可变参数的函数。

  • 考虑对可变参数的函数提供一个额外的固定元数的版本,从而使使用者无需借助apply方法。

// 多参数函数function multArgsFunc() {      console.log(arguments); //[1, 2, 3, 4, 5]    var sum = 0;    for(var i = 0; i < arguments.length; i++) {        sum += arguments[i];    }    return sum;}console.log(multArgsFunc(1, 2, 3, 4)); // 10console.log(multArgsFunc(1, 2, 3, 4, 5)); // 15

注意:

  1. 永远不要直接修改arguments对象

  2. arguments 是一个对象,不是数组,可以通过 [].slice.call(arguments) 将其复制到一个真正的数组中再进行操作

  3. 当使用 arguments 时当心函数嵌套,通常应该使用变量保存 arguments 的引用

apply

  • 使用apply方法指定一个可计算的的参数数组来调用可变参数的函数。

  • 使用apply方法的第一个参数给可变参数的的方法提供一个接收者。

注意:

apply的用法和call类似,唯一的区别在于call不接受参数数组,而apply可以接受参数数组,即使参数个数固定只有一个或两个,使用apply时也需要将参数用 [] 包裹起来,例子如下:

// 使用applyfunction compute() {    var sum = 0;    for(var i = 0; i < arguments.length; i++) {        sum += arguments[i];    }    return sum;}function wrapper(arr) {    return compute.apply(null, arr); // 给compute函数传递多个参数}var arr = [1, 2, 3, 4, 5];console.log(wrapper(arr)); // 15

bind

使用 bind 来提取具有确定接受者的方法

  • 要注意, 提取一个方法不会将方法的接受者绑定到该方法的对象上。

  • 当给高阶函数传递对象方法时,使用匿名函数在适当的接受者上调用该方法。

  • 使用bind方法创建绑定到适当接收者的函数。

  • 调用 f.bind(someObject) 会产生一个新的函数对象。在这个新的函数对象中,this被永久绑定到了bind的第一个参数上面,无论后期这个新的函数被如何使用。

示例如下:

function f(){    return this.a;}var g = f.bind({a:"jack"});console.log(g()); // jackvar o = {a:37, f:f, g:g};console.log(o.f(), o.g()); // 37, jackfunction Person(name){ this.nickname = name; this.distractedGreeting = function() {    setTimeout(function(){     console.log("Hello, my name is " + this.nickname);   }, 500); }} var alice = new Person('Alice');alice.distractedGreeting();//Hello, my name is undefinedfunction Person(name){  this.nickname = name;  this.distractedGreeting = function() {    setTimeout(function(){      console.log("Hello, my name is " + this.nickname);    }.bind(this), 500); // <-- this line!  }} var alice = new Person('Alice');alice.distractedGreeting();// after 500ms logs "Hello, my name is Alice"this.x = 9; var module = {  x: 81,  getX: function() { return this.x; }}; module.getX(); // 81 var getX = module.getX;getX(); // 9, 因为在这个例子中,"this"指向全局对象 // 创建一个'this'绑定到module的函数var boundGetX = getX.bind(module);boundGetX(); // 81

3、不要信赖函数的对象的toString方法

  • 当调用函数的toString方法时,并没有要求JavaScript引擎能够精确地获取到函数的源代码。

  • 由于在不同的引擎下调用toString方法的结果可能不同,所以绝对不要信赖函数源代码的详细细节。

  • toString方法的执行结果并不会暴露存储在闭包中的局部变量值。

  • 通常情况下,应该避免使用函数对象的toString方法。

(function(x) {    return x + 1;}).toString();/* * 输出结果 * function (x) { *  return x + 1; * } * */(function(x) {    return x + 1;}).bind(10).toString();/* * 由于使用了宿主环境的内置库提供的函数,JavaScript引擎会视图提供该函数的源代码的真实表示 * 而宿主环境中bind通常是其他语言(如C++)提供的是一个编译后的函数 * function (x) { [native code] } * */(function(x) {    return function(y) {        return x + y;    }}).bind(20).toString();/* * function () { [native code] } * */

转载地址:http://hjntl.baihongyu.com/

你可能感兴趣的文章
Rails Controller中的concerns测试编写
查看>>
RecyclerView使用指南(五)—— 实现吸顶效果
查看>>
[网络通信] OSI七层模型思维导图
查看>>
【BZOJ】3038: 上帝造题的七分钟2 && 3211: 花神游历各国
查看>>
java多线程(ExecutorService)
查看>>
CentOS Yum 源搭建
查看>>
前后端交互总结1: 软件架构与PHP搭建
查看>>
智能合约从入门到精通:JIDE集成开发工具
查看>>
leetcode-278-First Bad Version(注意不要上溢)
查看>>
招聘贴:蚂蚁金服招前端开发
查看>>
WKWebView获取H5页面里图片地址以及图片相对视图窗口的坐标的方法
查看>>
drools规则引擎笔记(二)
查看>>
T4模版引擎之基础入门
查看>>
第5组-17级通信工程3班-037-网络协议抓包分析
查看>>
【算法学习笔记】04.C++中结构体定义练习(bign初步)
查看>>
「小程序JAVA实战」小程序注册界面的开发(29)
查看>>
14.NPM 常用命令
查看>>
YUM 安装及清理
查看>>
【SSH网上商城项目实战15】线程、定时器同步首页数据(类似于CSDN博客定期更新排名)...
查看>>
删除对象中的元素的方法
查看>>