zoukankan      html  css  js  c++  java
  • 经典面试题简单分析

      var a = {n: 1}
      var b = a
      a.x = a = {n: 2}
    
      console.log(a.n, b.n) //2 1
      console.log(a.x, b.x) //undefined { n:2 }

    这是一道经典面试题,看似简单,其实暗藏玄机。

    至于对象赋值地址大家应该早已知道

    关键在于第三句  a.x = a = {n: 2}  考察了两个基本点 :点语法和=语法的优先级 2 连等的赋值操作

    分析:点语法比赋值优先级高,所以先执行点语法然后执行赋值,单纯你的以为a.x的点语法和离他最近的赋值=比较吗?(产生这想法的原因是大家都知道连等是从右往左赋值的,右边的等号在赋值的时候我a.x完全可以不用动)是连等的两个赋值等号比较,所以在a={ n : 2 } 之前就已经在a的空间里创建了一个x,并不是a={ n : 2 }之后才去创建。

    详细的js连等介绍:http://www.cnblogs.com/xxcanghai/p/4998076.html

    ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

    var x = 10
      function fn() {
        console.log(x)
      }
      function show(f) {
        var x = 20
        f()
      }
      show(fn) //10

    这道题从show(fn)来看,找到show函数传了一个fn函数,并执行fn,然后跟踪到fn的函数体,是要打印x

    问题来了?打印的是全局的x还是show里面的x。乍一看因为执行fn的时候是在show里面调用的所以打印了20,实际上函数不管在哪调用,都要返回他原本声明的地方去执行,因为把函数当做实参传进去就是传的地址,如果是用arguments就是传的函数内容。

    ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

    var fn = function () {
        console.log(fn)
      }
      fn() // fn函数体
      var obj = {
        fn2: function () {
          console.log(this.fn2)
        }
      }
    obj.fn2()

    fn()打印比较简单,就是打印自己本身这个函数体

    obj.fn2()调用了obj的方法,那么fn2中的this指向谁?在简单定义的对象中,方法中的this指向当前对象,非方法中的this指向window,所以打印的fn2函数体

    ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

      var c = 1;
      function c(c) {
        console.log(c);
        var c = 3;
      }
      console.log(c); // 1
      c(2); // c is not a function

    本题考查预解析:函数声明比var声明的更要前(本题没有用到,主要用到变量名提升在原地赋值),所以c早已变成1

    ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

    var name = 'World!'
      ;(function () {
        if (typeof name === 'undefined') {
          var name = 'Jack'
          console.log(name)
        } else {
          console.log(name)
        }
    })() // jack

    本题考查函数自调用。再次强调一点,在js运行的预解析阶段只要有var 声明就要变量提前(千万别以为if是条件所以可能不在执行语句中,预解析还没执行呢,只是解析)

    ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

    var a = 6
      setTimeout(function () {
        console.log(0)
        alert(a)
        a = 666
      }, 0)
      console.log(1)
      a = 66

    本题考查主线程和异步的执行顺序,显然是主线程先执行,所以弹出66

    ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

    function A () {
      }
      A.prototype.n = 1
      var b = new A()
      A.prototype = {
        n: 2,
        m: 3
      }
      var c = new A()
      console.log(b.n, b.m, c.n, c.m) // 1 undefined 2 3

    本题考查的是先new 再改原型,之前new的实例会不会受影响(原理还是地址指向问题)

    ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

    var F = function(){}
      Object.prototype.a = function(){
        console.log('a()')
      }
      Function.prototype.b = function(){
        console.log('b()')
      }
      var f = new F()
    
      F.a() // a()
      F.b() // b()
      f.a() // a()
      f.b() // f.b is not a function

    此题考查对函数也是对象在原型链上的提现:首先定义了一个函数F,相当于实例了一个函数即F.__proto__ ===  Function.prototype, Function.prototype === Object.prototype。

    最后,考查沿着原型链查找,找不到返回undefined。

    F.a()找到顶层Objecet,prototype上的方法,F.b()找到Function.prototype的方法

    f.a()找到顶层Objecet,prototype上的方法(f也是一个对象所以顶层还是Objecet,prototype) ,但是f.b()在原型上找不到,注意此时f的原型不是Function.prototype,而是F.prototype,而顶层Object.prototype也找不到b方法所以报错

  • 相关阅读:
    Atitit 华为基本法 attilax读后感
    Atitit 华为管理者内训书系 以奋斗者为本 华为公司人力资源管理纲要 attilax读后感
    Atitit 项目版本管理gitflow 与 Forking的对比与使用
    Atitit 管理的模式扁平化管理 金字塔 直线型管理 垂直管理 水平管理 矩阵式管理 网状式样管理 多头管理 双头管理
    Atitit 乌合之众读后感attilax总结 与读后感结构规范总结
    深入理解 JavaScript 异步系列(4)—— Generator
    深入理解 JavaScript 异步系列(3)—— ES6 中的 Promise
    深入理解 JavaScript 异步系列(2)—— jquery的解决方案
    深入理解 JavaScript 异步系列(1)——基础
    使用 github + jekyll 搭建个人博客
  • 原文地址:https://www.cnblogs.com/wchjdnh/p/10742923.html
Copyright © 2011-2022 走看看