随记

226 阅读5分钟

call、apply、bind 的用法分别是什么?

首先,要明白这三个函数的存在意义是什么?答案是改变函数执行时的上下文,再具体一点就是改变函数运行时的this指向。有了这个认识,接下来我们来看一下,怎么使用这三个函数。

  let obj = {name: 'tony'};
  
  function Child(name){
    this.name = name;
  }
  
  Child.prototype = {
    constructor: Child,
    showName: function(){
      console.log(this.name);
    }
  }
  var child = new Child('thomas');
  child.showName(); // thomas
  
  //  call,apply,bind使用
  child.showName.call(obj);
  child.showName.apply(obj);
  let bind = child.showName.bind(obj); // 返回一个函数
  bind(); // tony

  • call、apply与bind的差别

call和apply改变了函数的this上下文后便执行该函数,而bind则是返回改变了上下文后的一个函数。

  • call、apply的区别

他们俩之间的差别在于参数的区别,call和apply的第一个参数都是要改变上下文的对象,而call从第二个参数开始以参数列表的形式展现,apply则是把除了改变上下文对象的参数放在一个数组里面作为它的第二个参数。

function add(a,b){
    return a+b;
}
add.call(add, 5, 3); //8
add.apply(add, [5, 3]); //8

请说出至少 10 个 HTTP 状态码,并描述各状态码的意义。

HTTP协议状态码表示的意思主要分为五类,大体是:

  • 1××:保留
  • 2××:表示请求成功地接收
  • 3××:为完成请求客户需进一步细化请求
  • 4××:客户错误
  • 5××:服务器错误

状态码 200 表示响应成功

状态码206表示部分内容,服务器处理了部分get请求

状态码301表示永久重定向,被请求的资源已永久移动到新位置,并且将来任何对此资源的引用都应该使用本响应返回的若干个URI之一

状态码302表示临时重定向,请求的资源现在临时从不同的响应请求

状态码400表示错误请求,web服务器通过返回HTTP 400告诉访问者,访问者用来访问的网址程序出错,或访问途中请求途中遭到破坏。

状态码401表示未经授权,访问者访问受限页面未经授权,网站返回HTTP 401错误。

状态码403表示禁止访问,

状态码404表示文件未找到。

状态码500表示内部服务器错误。

状态码502表示无效网关。

DOM相关事件:什么是事件委托、怎么阻止默认动作、怎么阻止事件冒泡?

1:什么是事件委托:

通俗的讲,事件就是onclick,onmouseover,onmouseout,等就是事件,委托呢,就是让别人来做,这个事件本来是加在某些元素上的,然而你却加到别人身上来做,完成这个事件。也就是:利用冒泡的原理,把事件加到父级上,触发执行效果。

2:阻止默认事件

有一些html元素默认的行为,比如说a标签,点击后有跳转动作;form表单submit类型的input有一个默认提交跳转事件;reset类型的input有重置表单行为。如果你想阻止这些浏览器默认行为,JavaScript为你提供了方法。


 var $a = document.getElementsByTagName("a")[0];
 $a.onclick = function(e){
     alert("跳转动作被我阻止了")
     e.preventDefault();
     //return false;//也可以
 }

默认事件没有了。既然return false和e.preventDefault()都是一样的效果,那它们有区别吗?当然有。

仅仅是在HTML事件属性 DOM0级事件处理方法中 才能通过返回return false的形式组织事件宿主的默认行为。

3:阻止冒泡事件:

function stopBubble(e){
  if(e&&e.stopPropagation){//非IE
   e.stopPropagation();
  }
  else{//IE
   window.event.cancelBubble=true;
  }
 } 


记录平时易错得的知识点(一直更新)

分析js中fn()和return fn()的区别

在js中,经常会遇到在函数里调用其它函数的情况,这时候会有 fn() 这种调用方式,还有一种是 return fn() 这种调用方式,一些初学者经常会被这两种方式给绕晕了。这里用一个优雅的面试题来分析一下两种方式的不同之处。

var i = 0;
function fn(){
 i++;
 if(i < 10){
 fn();
 }else{
 return i;
 }
}
 
var result = fn();
console.log(result); 

这是一道隐藏了坑的面试题,看似很简单,大部分人可能想都不想就答出了10。而实际上运行可知打印出来的是 undefined。这道陷阱题很直观的体现出了前面所说的问题,当我们将执行fn的那一行修改为: 

var i = 0;
function fn(){
 i++;
 if(i < 10){
 return fn();
 }else{
 return i;
 }
}
 
var result = fn();
console.log(result); 

这时,会发现打印出来的结果终于不负众望的是 10 了。

为什么这里加不加return区别会这么大? 

这里的主要原因很简单,JavaScript的函数都是有默认返回值的,如果函数结尾不写return,会默认返回undefined,这就是为什么在chrome的console控制台里,写代码经常下面会出现一行undefined的原因。 再仔细看看这个例子,当i自增到9的时候,也就是倒数第二次递归调用fn的那一次,如果没有return,这一次执行完fn,会默认return undefined,而不会继续下一次递归了。当加上了 return,在这里则会继续最后一次递归,即i=10的时候,跳入else里面返回得到正确的10。 

字符串模板和非字符串模板

HTML 特性是不区分大小写的。所以,当使用的不是字符串模板时,camelCase (驼峰式命名) 的 prop 需要转换为相对应的 kebab-case (短横线分隔式命名)

 Vue.component('child', {
// 在 JavaScript 中使用 camelCase
props: ['myMessage'],
template: '<span>{{ myMessage }}</span>'
})
<!-- 在 HTML 中使用 kebab-case -->
<child my-message="hello!"></child>

 如果你使用字符串模板,则没有这些限制。 嗯,还是上面说过的,看到这里,不知道字符串模板是啥,非字符串模板是啥.....下面就来说道说道! 字符串模板:指的是在组件选项里用 template:"" 指定的模板,换句话说,写在 js 中的 template:"" 中的就是字符串模板。比如下面这个:

var tmp = new Vue({
    template:"<myComponent></myComponent>"
});

非字符串模板:在单文件里用 <template></template> 指定的模板,换句话说,写在 html 中的就是非字符串模板。