Definition of function

  • Custom functions (named functions)

    function fn() {};
    Copy the code
  • Function expressions (anonymous functions)

    var fun = function() {};
    Copy the code
  • New Function (‘ parameter 1’, ‘parameter 2′,’ parameter 3′);

    var f = new Function('a'.'b'.'console.log(a + b)');	// Statements are printed directly as strings
    f(1.2);  / / the argument
    Copy the code
    • All functions are instances of Function.

Second, function call

  1. The ordinary function this points to the window

    function fn() {
        console.log('hi');
    }
    window.fn();
    fn.call();
    Copy the code
  2. Object method this refers to object O

    var o = {
        sayHi: function() {
            console.log('hi');
        }
    }
    o.sayHi();
    Copy the code
  3. The constructor this refers to the instance cy, and this in the prototype (star.prototype.sing) also refers to the instance cy

    functoin Star() {
        console.log('hi');
    }
    var cy = new Star();
    Copy the code
  4. The binding event function this points to the caller BTN

    btn.onclick = function() {
        console.log('hi');
    }
    Copy the code
  5. The timer function this points to the window

    window.setInterval(function() {
         console.log('hi');
    },1000)
    Copy the code
  6. Execute the function immediately –> automatically call this to point to the window

    (function() {
         console.log('hi'); }) ()Copy the code

1. Change the internal direction of the function

1). call

fun.call (thisArg, arg1, arg2, ...)
Copy the code
  • Call a function
  • Change the this pointer inside the function
        var o = {
            name: 'Andy'
        }
        function fn(a,b) {
            console.log(this);	// {name:"Andy"}
            console.log(a+b);	/ / 3
        }
        fn.call(o, 1.2);
Copy the code
  • inheritance

		function Father(uname, age){
            this.uname = uname;
            this.age = age;
        }
        function Son(uname, age, score){
            // Call the parent constructor to change this in the parent constructor to this in the child constructor
            Father.call(this, uname, age);
            this.score = score;
        }
        var six = new Son('spring Yang'.21.100);
        console.log(six);
        //Son {uname: "spring ", age: 21}
        //age: 21
        //uname: "spring poplar"
        //__proto__: Object
Copy the code

2). apply

fun.apply(this.Arg, [argArry])
Copy the code
  • Must be passed as an array

  • Call a function

  • Change the this pointer inside the function

  • Use mathematical built-in objects

        var o = {
            name: 'Andy'
        }
        function fn(arr) {
            console.log(this);  // {name: "Andy"}
            console.log(arr);   // pink
        }
        fn.apply(o,['pink']);

        var arr = [6.7.3.8];
        var max = Math.max.apply(Math, arr);
        console.log(max);	/ / 8
Copy the code

3). bind

fun.bind (thisArg, arg1, arg2, ...)
Copy the code
  • Change the this pointer inside the function

Bind only, not call

        var o = {
            name: 'Andy'
        }
        function fn(arr) {
            console.log(this);
        }
        var f = fn.bind(o); // bind only, no call
        f();
Copy the code
Click < button > < / button ><button>Click on the</button>
    <button>Click on the</button>
    <script>
        // There is a button. When we click it, we disable it. After 3 seconds, we turn it on
/* var btn = document.querySelector('button'); btn.onclick = function() { this.disabled = true; SetTimeout (function() {this.disabled = false; }.bind(this), 1000) } */

        var btn = document.querySelectorAll('button');
        for(var i = 0; i < btn.length; i++) {
            btn[i].onclick = function() {
                this.disabled = true;
                setTimeout(function() {
                this.disabled = false;
                }.bind(this), 1000)}}</script>    
Copy the code

Three, strict modeuse strict

1. Enable strict mode for the script

<script> 
  (function (){
    "use strict"; }) (); </script>Copy the code

To place the entire script file in an anonymous function that executes immediately. This creates a scope independently of other script script files.

2. Turn on strict mode for functions

function fn(){
    "use strict";   
    return "This is strict mode."; 
} 
Copy the code

Strict mode is turned on for a function.

3. Changes in strict mode

1). The variable

  • Variables must be declared with the var command first.

  • Do not delete declared variables. For example, delete x; The grammar is wrong.

2). This refers to the problem

before Strict mode
This in a global scoped function refers to an object window undefined
The constructor Do not addnewCan also be called, as a normal function, this refers to a global object Without the new call, this refers to undefined, and assignment will report an error
The new instantiated constructor points to the created object instance
The timer this still points to the window
Event, object, or point to the caller
function Star() {
     this.sex = 'male';
 }
 var ldh = new Star();
 console.log(ldh.sex);
Copy the code

3.) function

  • Functions cannot have arguments with the same name.
  • Functions must be declared at the top level.
  • It is not allowed to declare functions inside non-function blocks of code.

Higher order functions

Operations on other functions that accept functions as arguments or output functions as return values.

        function fn(a, b, callback) {
            console.log(a + b);
            callback && callback();
        }
        fn(1.2.function() {
            console.log('I'm calling last.');
        });

        $("div").animate({
            left: 500
        }, function() {$("div").css("backgroundColor"."purple");
        })
Copy the code

Five, the closure

1. Variable scope

  • Divided intoThe global variableandA local variable
    • Global variables can be used inside functions.
    • Local variables may not be used outside functions.
    • Local variables in this scope are destroyed when the function completes execution.

2. The closure

A scope can access local variables inside another function.

Main function: extended the scope of the variable.

        function fn() {
            var num = 10;
            function fun() {
                console.log(num);
            }
            fun();
        }
        fn();
		// the fun function scope accesses the local variable num in another function fn
Copy the code
        function fn() {
            var num = 10;
            function fun() {
                console.log(num);
            }
            return fun;
        }
  	  // The scope outside fn can also access the variable s inside fn
        var f = fn();
        f();
Copy the code
        function fn() {
            var num = 10;
            return function () {
                console.log(num); }}var f = fn();
        f();
Copy the code

Case 3.

  1. Dynamically adding properties
var lis = document.querySelector('.nav').querySelectorAll('li');
        for(i = 0; i < lis.length; i++){
            lis[i].index = i;   // Add attributes dynamically
            lis[i].onclick = function() {
                console.log(this.index); }}Copy the code
  1. Use closure to get the index number of Li
for(i = 0; i < lis.length; i++){
            // Use the for loop to create four immediately executed functions
            (function(i) {  // Must be passed in through the following parentheses
                // console.log(i);
                lis[i].onclick = function() {
                    console.log(i); // The I inside this function is the contents of another function where the closure is generated.
                }
            })(i);
        }
Copy the code

The immediate function also becomes a small closure because any function inside the immediate function can use its I variable

  1. Print all li elements after 3 seconds
        for(var i = 0; i < lis.length; i++){
           (function(i) {
               setTimeout(function() {
                   console.log(lis[i].innerHTML)
               },3000);
           })(i);
        }
Copy the code
  1. Calculate the price of a taxi
    • Taxi fare starts at 13(within 3 kilometers) and increases by 5 yuan for each additional kilometer. Users enter the mileage to calculate the fare
    • If there is congestion, the total price will be charged 10 yuan more congestion charge
        var car = (function() {
            var start = 13;
            var total = 0;
            return{
                price: function(n) {
                    if(n <= 3){
                        total = start;
                    }
                    else{
                        total = start + (n - 3) *5;
                    }
                    return total;   // Return must be returned.
                },   / / normal
                yd: function(flag) {    / / congestion
                    return flag ? total + 10 : total;   // Is it congested? True total+10: false total}}}) ();console.log(car.price(5)); / / 23
        console.log(car.yd(true)); / / 33

        console.log(car.price(1)); / / 13
        console.log(car.yd(false)); / / 13
Copy the code

4. There is

      var name = "The Window";
      var object = {
          name: "My Object".getNameFunc: function() {
              return function() {
                  return this.name;   // This refers to the anonymous function -> function immediately executes the function that window contains}; }};console.log(object.getNameFunc()());		// The Window
      
      var f = object.getNameFunc();
      / / similar to
      var f = function() {
          return this.name;
      }
      f();
Copy the code

Are there closures? No. No global variables

        var name = "The Window";varobject = {name: "My Object".getNameFunc: function() {
                var that = this;
                return function() {
                    returnthat.name; }; }};console.log(object.getNameFunc()());        //My Object
Copy the code

Are there closures? That is a local variable.

Sixth, the recursion

  • The function calls itself.

  • Similar to the for loop

  • Keep opening new space => Stack overflow => Must add exit condition => return

        function fn() {
            fn();
        }
        fn();
Copy the code

        var num = 1;
        function fn() {
            console.log("hello")
            if(num == 6) {return;
            }
            num++;
            fn();
        }
        fn();
Copy the code

1. Problem solving

1.) recursion

        function fn(n) {
            if(n == 1) {return 1;
            }
            else {
                return n * fn(n-1); }}console.log(fn(3));
Copy the code

2). Fibonacci sequence

        function fn(n) {
            if(n == 1 || n == 2) {return 1;
            }
            else {
                return fn(n-1) + fn(n-2); }}console.log(fn(3));
Copy the code

2. Shallow copy and deep copy

1). A shallow copy

  • Only one layer is copied, and only references are copied at the deeper object level
		var obj = {
			id: 1.name: 'andy'
		};
		var o = {};
		for(var k in obj) {
			Obj [k] is the value of the attribute
			o[k] = obj[k];	// The same as O.k => O.name/O.id
		}
		console.log(o);		// new.html:20 {id: 1, name: "andy"}
Copy the code
  • The deeper object can be copied but it’s the address

MSG is an object that creates a new space in memory for age:18

The address copied is the same as the data stored in the original OBJ

Two points to one data and if you modify the data in O it will affect the data in OBj

		var obj = {
			id: 1.name: 'andy'.msg: {
				age: 18		// Deeper objects}};var o = {};
		for(var k in obj) {
			Obj [k] is the value of the attribute
			o[k] = obj[k];	// The same as O.k => O.name/O.id
		}
		console.log(o);
Copy the code
  • In the ES6 increasedObject.assign(target,... source)implementationShallow copy

Target: Copy to whom

Source: Copy that object

		var obj = {
			id: 1.name: 'andy'.msg: {
				age: 18		// Deeper objects}};var o = {};
		Object.assign(o,obj);
		console.log(o);
Copy the code

2). A deep copy


		var obj = {
			id: 1.name: 'andy'.msg: {
				age: 18		// Deeper objects
			},
			color: ['red'.'pink']};var o = {};
		// Use function recursion to iterate first over the outside and then over the inside of the deeper object
		// Encapsulate the function
		function deepCopy (newobj,oldobj) {
			for(var k in oldobj) {
				// Determine whether the attribute value is of a simple type or a deeper type
				Oldobj [k]
				var item = oldobj[k];
				// 2. Check whether the data type is array
				if(item instanceof Array) {		// Put arrays on top because arrays are also objects
					newobj[k] = [];
					deepCopy(newobj[k], item);
				}
				// 3. Check whether it is an object
				else if(item instanceof Object) {	// This is the data type
					newobj[k] = {};
					deepCopy(newobj[k], item);
				}
				// 4. None of these are simple data types
				else{
					newobj[k] = item;
				}
			}
		}
		deepCopy(o, obj);
		console.log(o);
Copy the code

At this point, changing o will not have any effect on OBj, okay