每天3小时学前端之JS-第13天-函数的声明-函数名提升

636 阅读3分钟

此系列体验视频教程

点击观看:哔哩哔哩

函数

函数内部保存的是一段可以执行的代码。

函数的声明与调用

JavaScript 有三种声明函数的方法。

1. 声明式定义函数(Function Declaration)

  • function命令后面是函数名
  • 函数名后面的小括号中是传入函数的参数
  • 大括号中放的是函数体
function fn(param) {
  console.log(param);
}

2. 函数表达式(Function Expression)

  • 将一个匿名函数赋值给变量
  • function命令后面不带有函数名
  • 如果加上函数名,该函数名只在函数体内部有效,在函数体外部无效
var fn = function(param) {
  console.log(param);
};
var fn1 = function fn2(){
  console.log(typeof fn2);
};

fn2
// ReferenceError: fn2 is not defined

fn1()
// function
函数的name属性
  • 声明式函数的name输入自然就是函数名
  • 表达式函数的name属性分两种情况
    • 赋值的函数为匿名函数
      • 函数的name即为变量名
    • 赋值的函数为具名函数
      • 函数的name属性为具名函数名,此具名函数只能在具名函数内部调用
      • 在外部依然使用变量名来调用函数
function fn() {

}
console.log(fn.name); // fn
var fn1 = function () {
      
}
console.log(fn1.name); // fn1

var fn2 = function fn2Name() {
  console.log(typeof fn2Name);
}
console.log(fn2.name); // fn2Name
fn2() // 'fnction'
console.log(typeof fn2Name); // undefined

3. Function 构造函数

  • Function构造函数接受三个参数
  • 最后一个参数是add函数的“函数体”
  • 其他参数(可以多个)都是add函数的参数
  • 如果只有一个参数,该参数就是函数体
var add = new Function(
  'x',
  'y',
  'console.log(x + y)'
);

// 等同于
function add(x, y) {
  console.log(x + y)
}

小括号运算符和return语句

  • 使用小括号运算符调用函数。
  • 小括号之中,可以加入函数的参数。
  • 函数体内部的return语句,表示返回紧跟return后面的表达式的值
  • 函数只执行到return语句,return语句以下的代码不会被执行
  • 没有使用return语句的函数,返回undefined
function add(x, y) {
  return x + y;
}

add(1, 1) // 2

函数名的提升

JS引擎将函数名视同变量名。采用function命令声明函数时,函数名变量名类似都会被提升到代码的头部,又因为声明的函数就必然会有函数体,也就意味着只要当前文件声明了某个函数,那么在声明函数之前,甚至是代码头部就可以调用。

可以和变量的声明提升做一个对比,由于变量的声明赋值分开的,所以如果在代码头部打印当前文件中声明并赋值的变量的时候,结果就是undefined,因为赋值在下面。 所以,下面的代码不会报错。

fn();

function fn() {}

但是,如果采用函数表达式,就会报错。

f();
var f = function (){};
// TypeError: undefined is not a function

上面的代码等同于下面的形式。

var fn;
f();
fn = function () {};

同时采用声明式函数表达式声明同一函数,由于声明式函数的变量提升,在函数表达式之前调用则会调用声明式函数,函数表达式之后调用则会调用函数表达式所定义的函数。

练习

  • 判断以下代码的打印结果
// 1
function fn(a, b) {
  if (a < b) {
    return a + b
  } else if(a == b) {
    return a / b
  }
  return a * b
}
console.log(fn(6, 3));

// 2
/* function fn(a, b) {
  if (a < b) {
    return a + b
  } else {
    return a / b
  }
  return a * b
}
console.log(fn(6, 3)); */

// 3
/* function fn(a, b) {
  if (a < b) {
    return a + b
  } else if(a == b) {
    return a / b
  }
  return a * b
}
console.log(fn(3, 6)); */
  • 判断以下代码的打印结果
var fn1 = 123
var fn1 = function() {
  return 456
}
console.log(fn2());
function fn2() {
  var result = fn1()
  return result
}
function fn1() {
  return 789
}

/* var fn1 = 123
console.log(fn2()); // 使用函数的时候要关注函数调用的位置
var fn1 = function() {
  return 456
}
function fn2() {
  var result = fn1()
  return result
}
function fn1() {
  return 789
} */


/* var fn1 = 123
function fn1() {
  return 789
}
console.log(fn2());
var fn1 = function() {
  return 456
}
function fn2() {
  var result = fn1()
  return result
} */

作业

  • x的n次方

声明一个函数fn,接收两个参数x和n,最终返回x的n次方的结果