JavaScript基础(06_函数)

函数

Function

  • 函数也是一个对象

  • 函数中可以封装一些功能(代码块),在需要时可以执行这些功能

  • 函数中可以保存一些代码,在需要时候进行调用

创建函数对象

  • 可以将要封装的代码以字符串的形式传递给构造的函数

  • 封装到函数中的代码不会立即执行

  • 函数中的代码会在函数调用时执行

    • 调用函数语法: 函数对象()

    • 当调用函数时,函数中的代码会按照顺序立即执行

    • var fun = new Function();
      console.log(fun);
      console.log(typeof fun);
  • 方法一:使用函数声明 来创建一个函数 (经常使用)

    • 语法:

    • function 函数名([形参1,形参2,形参3,形参4...]){
      语句...
      }
    • function fun2(){
        console.log("first");
        console.log("second");
        console.log("third");
      ​
      }
      console.log(fun2);
      fun2();
  • 方法二:使用函数表达式创建一个函数

    • 语法:

    • var 函数名 = function(){
      语句
      }
    • var fun3 = function(){
        console.log("我是匿名函数中封装的代码");
      }
      fun3();
  • 方法三:创建一个构造函数,专门用来创建Person对象

    • 构造函数就是一个普通函数,创建方式和普通函数没有区别

    • 不同的是,构造函数习惯上首字母大写

    • 构造函数和普通函数的区别就是调用方式不同

    • 普通函数就是直接调用,而构造函数需要使用new关键字来调用

    • 构造函数的执行流程

      • 立刻创建一个新的对象

      • 将新建的对象设置为函数中的this,在构造函数中可以使用this来引用新建对象

      • 逐行执行函数体代码

      • 将新建的对象作为返回值返回

      • 使用他同一个构造函数创建的对象,称之为一类对象,也将一个构造函数称为一个类

      • 将通过一个构造函数创建的对象,也称为是该类的实例

    • this:

      • 当以函数的形式调用时,this是window

      • 当以方法的形式调用时,谁调用方法this就是谁

      • 当以构造函数的形式调用时,this就是新创建的那个对象

函数的参数

  • 函数形参

    • 可以在函数的括号中来制定一个或者多个形式参数(形参)

    • 多个形参之间 使用,隔开,声明形参就相当于在函数内部声明了对应的变量

    • 但是并没有赋值

  • 函数实参

    • 实参将会赋值给函数中对应的形参

    • 函数的实参可以是任意的数据类型

    • 注意:是否可能接收到非法的参数,所以需要尽量检查实参的类型

  • 函数调用

    • 调用函数时,解析器不会检查实参的数量

    • 多余的时实参不会被赋值

    • 如果实参的数量少于形参的数量,则没有对应实参的形参将自动填充为Undefined

  • function sum(a,b){
      console.log(a+b);
    }
    ​
    sum(123,456);
    sum(123);

传递隐藏的参数

  • 在调用函数时,浏览器每次都会传递进两个隐含的参数

    • 函数的上下文对象this

    • 封装实参的对象 arguments

      • arguments是一个类似数组的对象,他也可以通过索引来操作数据,也可以获取长度

      • 在调用函数时,我们所传递的实参都会在arguments保存

      • arguments.length可以来获取实参的长度

      • 即使没有定义形参,也可以通过arguments来使用实参

      • 获取实参与数组一致

      • arguments的一个callee属性,对应当前正在执行函数的对象

函数的返回值

  • 创建一个函数,用来计算三个数的和

  • function sum(a,b,c){
      var d = a + b + c;
      return d;
    }
    ​
    // 调用函数
    // sum(1,2,3);
    var ret = sum(1,2,3);
    alert(ret);

函数作用域

  • 作用域

    • 作用域指一个变量的作用的范围

    • js中共有两种作用域

      • 全局作用域

        • 直接编写在script标签中的js代码,都在全局作用域中

        • 全局作用域在页面打开时创建,在页面关闭时销毁

        • 在全局作用域中有一个全局对象window ,可以直接使用

        • window代表浏览器的窗口

        • 在全局作用域中:

          • 创建的变量都会作为window对象的属性保存

          • 创建的函数都会作为window对象的方法保存

        • 全局作用域中的变量都是全局变量

          • 页面中任意部分都可以访问到的变量

      • 函数作用域

        • 调用函数时创建函数作用域,函数执行完毕以后,函数作用域销毁

        • 每调用一次函数就会创建一个新的函数作用域 ,作用域之间相互独立

        • 在函数作用域中可以访问全局作用域中的变量

        • 全局作用域中无法访问到函数作用域中的变量

        • 函数作用域中操作一个变量,会先在自身作用域中寻找

          • 若有就直接使用

          • 若没有则往上一级去找

          • 一直到找全局作用域中的变量

          • 如果全局作用域中也没有该变量,则会报错ReferenceError

        • 在函数中想使用全局变量,可以使用window.变量名

        • 在函数作用域中也有声明提前的法则

        • 在函数中,如不使用var声明变量,则会设置为全局变量

        • 函数中定义形参,就相当于在函数作用域中声明了变量,如果再调用函数时没有传入实参,则其值为Undefined

变量提前声明

  • 变量的声明提前

    • 使用var关键字声明的变量,会在所有代码执行之前被声明,但是变量的赋值只能在执行到这行代码时进行

    • 如果声明变量时不使用var关键字,则变量不会被声明提前,代码可能会报错

  • 函数的声明提前

    • 使用函数声明形式创建的函数,function(){}

    • 他会在所有的代码执行之前会被创建( function(){} ),所以我们可以在函数声明前来调用函数

    • 使用函数表达式创建的函数( var fun=function(){} ),不会被声明提前,所以不能在声明前调用

  • // 案例一
    console.log(a);
    a = 123;
  • // 案例二
    console.log(a);
    var a = 123;

this

  • 解析器在调用函数时,每次都会向函数内部传递进一个隐含的参数

    • 这个隐含的参数就是this

    • this指向的是一个对象

    • 这个对象称为函数执行的上下文对象

    • 根据函数调用方式不同,this会指向不同的对象

      • 以函数形式调用时,this永远都是window

      • 以对象的方法形式调用时,this就是该方法的对象

      • var name = "xxx"
        function fun(){
          console.log(this.name);
        }
        var obj = {
          name:"Tom",
          sayName:fun
        };
        obj.sayName();
        fun();
    • // this的
      var name =  "全局";
      function fun(){
        console.log(this.name); //精髓是this
      };
      ​
      var obj1 = {
        name : "Tom",
        sayName : fun
      };
      ​
      var obj2 = {
        name : "Jack",
        sayName : fun
      };
      // 需求1:希望调用obj1.sayName()可以输出"Tom"
      // 需求2:希望调用obj1.sayName()可以输出"Jack"
      obj1.sayName();
      obj2.sayName();

工厂方法

  • 使用工厂方法创建对象,通过该方法可以大批量创建对象

  • function createPerson(name,age,gender){
      var obj = new Object();
    ​
      obj.name = name;
      obj.age = age;
      obj.gender = gender;
      obj.sayName = function(){
        alert(this.name);
      };
      return obj;
    }
    ​
    var obj2 = createPerson("Tom",28,"男");
    var obj3 = createPerson("Rose",18,"女");
    var obj4 = createPerson("Jack",48,"男");
    ​
    obj2.sayName();
    alert(obj2.age);

构造函数方法

  • function Person(name, age, gender){
      this.name = name;
      this.age = age;
      this.gender = gender;
      this.sayName = fun
    }
    ​
    function fun(){
      alert(this.name);
    }
    ​
    var per3 = new Person("swk",18,"male");
    var per4 = new Person("zbj",28,"female");
    var per5 = new Person("shs",38,"male");
    ​
    console.log(per3.sayName());
    console.log(per4.sayName());
    console.log(per5.sayName());
posted @ 2020-09-19 19:48  名叫蛐蛐的喵  阅读(113)  评论(0编辑  收藏  举报