函數學習筆記

函數的定義:
函數是一段能夠反覆調用的代碼塊,函數能夠接受輸入的參數,不一樣的參數返回值也不一樣
通俗的說函數就是一個工具,用來實現某個功能,具備封裝性javascript

函數的聲明有兩種方式:
第一種聲明方法: function命令
function fn () {
}java

第二種聲明方式:函數表達式
須要注意的是,函數表達式聲明函數,表達式後面須要加上分號,表示語句結束
var fn = function () {
};函數

注意:
第二種聲明方式,function後面不帶有函數名,若是加上函數名,該函數名只在函數內部有效,函數外部無效
var print=function x(){
  console.log(typeof x);
};
print(); //function
x(); //報錯
這種寫法的用處有兩個,一是能夠在函數體內部調用自身,二是方便除錯(除錯工具顯示函數調用棧時,將顯示函數名,而再也不顯示這裏是一個匿名函數)。工具


函數不得在條件語句中聲明函數
javascript規定不能夠在非函數代碼塊中聲明函數,好比在if語句,try語句中聲明函數
if(false){
  function ff(){}
}spa

因爲函數提高,致使上面的if語句無效遞歸

若是要實如今條件語句中聲明函數的目的,必須使用函數表達式聲明法ip

if(false){
  var ff1=function(){作用域

  }字符串

}源碼

ff1(); //報錯


函數名的提高:
javascript把函數名視同爲變量名,在預解析的時候會把整個函數提高到代碼頭部,因此function命令聲明的函數,能夠先調用後聲明

fn(); //不會報錯
function fn(){
  console.log(1);
}

可是函數表達式聲明的函數卻不能夠,由於js預解析的時候只是把變量聲明提到了代碼的最頂部,並無把賦值提高,在沒有賦值以前,變量的值爲undefined
fn1(); //報錯 fn1不是一個函數
console.log(typeof fn1); // undefined
var fn1=function(){
  console.log(2);
}


注意:同時採用賦值語句和function命令聲明同一個函數,最後老是採用賦值語句聲明的函數


遞歸函數:
函數的內部能夠調用自身,這就是遞歸函數

function fib(num){
  if(num===0){
    return 0;
  }
  if(num===1){
    return 1;
  }
  return fib(num-2)+fib(num-1);
}

函數中的return語句
函數體內部的return語句,表示返回。javascript引擎遇到return語句,就返回return後面的那個表達式的值,後面即便還有語句,也不會獲得執行,也就是說return語句後面的那個表達式值就是函數的返回值,return語句不是必須的,若是不寫,函數就不返回任何值,或者返回undeifned

函數的屬性和方法:
1.函數的length屬性返回的是函數預期返回的參數的個數,也就是函數聲明時候參數的個數

function fn(a,b){
  return a+b;
}

console.log(fn.length);

fn(1);
console.log(fn.length);

fn(1,2,3);
console.log(fn.length);

2.name屬性返回的是緊跟在function關鍵字後面的那個函數名
function f1(){

}

console.log(f1.name); //f1

//將一個匿名函數賦值給一個變量
var f2 = function () {};
//那個這個函數的name屬性值在ES5下老是返回一個空字符串
console.log(f2.name); //""

//在ES6下作了修改,返回的是實際的函數名
console.log(f2.name); //f2

//真正的函數名仍是f3,myName這個名字只在函數體內部可用
var f3=function myName(){

}

console.log(f3.name); //myName


3.函數的toString方法返回函數的源碼
function f1(){
  console.log(123);
}

console.log(f1.toString());

function f2(){/*
這是一個
註釋
*/}
console.log(f2.toString());


實現多行字符串
function multiline(fn){
  var arr=fn.toString().split("\n");
  return arr.slice(1,arr.length-1).join("\n");
}
console.log(multiline(f2));
document.body.innerHTML="<pre>"+multiline(f2)+"</pre>";


函數的做用域:
做用域(scope)指的是變量存在的範圍。Javascript只有兩種做用域:一種是全局做用域,變量在整個程序中一直存在,全部地方均可以讀取;另外一種是函數做用域,變量只在函數內部存在。

在函數外面聲明的變量就是全局變量 能夠在函數內部讀取
var a=12;
function fn(){
  console.log(a);
}

fn(); //12

在函數內部定義的變量,稱爲局部變量,在函數外面讀取不到
function fn(){
  var c=23;
}

console.log(c); //報錯


函數內部定義的變量,會在做用域內覆蓋同名的全局變量

var f=12;
function f5(){
  var f=44;
  console.log(f);
}
f5(); //44
console.log(f); //12


對於var聲明的變量來講,只有在函數內部聲明的變量纔是局部變量,其餘區塊聲明的都是全局變量

if(true){
  var a=12;
}

console.log(a); //12


函數自己的做用域:
函數自己也是一個值,也有本身的做用域,函數的做用域就是其聲明時所在的做用域,與其運行時所在的做用域無關

var s=12;
function fn(){
  console.log(s);
}

function fn1(n){
  var a=24;
  n();
}

fn1(fn); //12

函數體內部聲明的函數,做用域綁定函數體內部。
function f2(){
  var n=33;
  return function f3(){
    console.log(n);
  }
}

var n=99;
f2()(); //33


函數內部變量的提高:
和全局做用域同樣,函數內部的做用域也會產生變量提高的現象,var聲明的變量,不論在什麼位置,變量聲明都會被提高到函數體內部的頂部

function fn(x){
  if(x>100){
    var temp=x-100;
  }
}

//等同於:
function fn(x){
  var temp;
  if(x>100){
    temp=x-100;
  }
}

相關文章
相關標籤/搜索