通过断点获取变量

小知识系列

平时在代码里,如果是IIFE(立即执行函数),比如:
(function(){var a = 1})
在浏览器里直接按F12,然后输入a,一般是会出现错误提示。这时如果选择sources选项卡,给这脚本相应的位置打上断点后,在刷新下,这时在操作台输入a就会打印1啦!

前端利用代理解决跨域问题

场景

前端:‘后端朋友,你那接口我访问不了,你设置下那个access-control-follow-origin?’
后端:'不要啦,那样容易会被CSRF攻击的啦,又不是测试服的接口,安全很重要的'

遇到这个问题,后端又不想配合你搞搞jsonp(其实也没必要,还真的浪费时间),肯定就要用 代理啦!

代理分为正向代理跟反向代理

正文

今天要讲的是利用fiddler这个软件实现正向代理。

我们新建一个index.html文件,然后该文件里引用js:

$.ajax({
        url: 'http://vote.sina.com.cn/api/survey/vote_status/240',
        method: "POST",
        data: {
            t: 1520434311162
        },
        success: function (data) {
            console.log(data);
        },
})

这个url是我在新浪首页随便找的,一运行index.html就会提示跨越问题:

XMLHttpRequest cannot load http://vote.sina.com.cn/api/survey/vote_status/240. No 'Access-Control-Allow-Origin' header is present on the requested resource. Origin 'null' is therefore not allowed access.

这时候fiddler就出场了,
打开该软件(其实谷歌浏览器也可以设置代理,原理一样,但我没试过。。。)

1.选择AutoResponder选择卡
2.勾上Enable rules
3.勾上Unmatched requests passthrough
4.填上 http://www.sina.com.cn
5.填上 index.html的路径(注意是文件路径,跟浏览器里路径的最大区别是‘/’跟‘\’)
6.点击有点的save按钮
好了,现在浏览器里输入http://www.sina.com.cn ,咋们不会跳到新浪首页,而会访问你那个index.html文件,然后在操作台可以看得请求的到数据了。

反向代理下次再聊,我知道webpack里可轻松设置,利用express服务端请求接口不存在跨域这个原理。
如果理解有误,欢迎指正。~

参考文章:
前端开发如何独立解决跨域问题
如何使用Fiddler实现跨域访问(把自己做的静态HTML页面域名变成api.bing.com)

kmp算法

一如既往,推荐看客先看阮一峰博客:字符串匹配的KMP算法

定义:

一大串字符串里找某字段算法

原理:

利用某字段自身特有的规律(前后缀,这个词有看上面那文章或了解过算法的人才知道我说啥),实现非暴力查找字符串的方法。

重点:

得到部分匹配表

心得:

我用js根据思路写了个模拟的代码,能用!
源码地址:戳我

效率

嗯。。。没js自带的indexOf快。
测试时我的代码x ms,indexOf 是 0.x ms,快一倍(废话,原生的肯定用了更好的算法,比如从两头开始算,我这只从一头开始算)。

题外话

为什么会接触这个算法呢,本来我在看别人的源码,然后不小心点到他的知乎,又不小心点到他点过赞的文章,然后看到个文章大概是有个人面试时手写了kmp算法,面试官还问他是不是hr漏题了呵呵之类。。。,然后我正事没做(买了个慕课网的vue视频),就去看这算法了,发现别人的代码理解不了,然后去看阮一峰的博客,哦思想懂了!然后尝试写代码,index索引不太清楚该+1还是-1什么的就拿笔画一画,整个过程用3,4小时(我就是这渣渣水平)。

心态变化:我擦好难-我还看吗-不知浪不浪费时间-别人源码写的啥-理解这思路-自己写写看-成功-开心

想着对学习的朋友说下,有时看不懂别人的代码不要心急,可能。。。你理解后自己能写出来,再去看别人的代码(或不看)也可以哦,我是这样过来的,一起加油!

DOM 中 Property 和 Attribute 的区别

刚刚偶然看到篇文章:
DOM 中 Property 和 Attribute 的区别
(强烈推荐先看完上文)
收获颇多,写写读后感跟注意到的点吧。

值得一提的是一般在表单中我们会用obj.value = xx或者用jq$(obj).value(xx)来改变input标签的值(这里的obj指input对象),改完后发现查看源代码中的input标签的value值还是原来的值,这个其实并不大会影响到我们提交的操作(这里适用于jq的表单serialize化)。
比如我们写了个input标签,id为'ha'
一顿操作后value值在浏览器界面是看到改变了,标签里的值还是没有变,这时我用jq的ajax+serialize提交表单
然后在浏览器f12后,network里看到
提交的值为2,也就是修改后的值。

其实看完那篇文章较大的收获还是通过jq源码了解了一些规范的函数写法
比如定义函数时

// 这是一个xx功能的函数,能够balalal

// @param a, a的定义
// @param b, b的定义
function test(a,b){
    //这里虽然参数有了b,但有时候不是为了传参用的,而是为了跟清楚的知道每个参数的定义
    //而不是如下这样写
    var b = xx;//bad
    //不用声明,直接
    b = xx;//good
}

后来我想了下,这只是让我知道了有这种写法而已,函数里变量一多都写到函数参数上面也不好看。嗯。。。就这样吧。

Jquery.extend与Object.assign

插曲

说到Jquery.extend就想到$.fn.extend,两者区别大了

前者可以把对象参数里的值加到jquery这个变量上,后者是把值加到jquery实例化后的对象上($.fn===$.prototype哦)。所以后者用于给jq扩展插件用的。

正言

$.extend一般情况下用起来跟Object.assign没什么不同
作用就是简单的便利每个对象参数里的key,相同则以后面对象参数(b)的key对应的value值覆盖前面(a)的key对应的value值。
这种方法经常被来用实例化组件时填写自定义的option来替换默认的option。(没听过的话,这里有个jq插件的源码,https://github.com/alvarotrigo/pagePiling.js/blob/master/jquery.pagepiling.js ,看到里面$.extend的应用就会明白了)。
如何你有看上面插件的源码,你会发现有点不一样的地方:$.extend(true,xxx,xxx)

没错,这次第一个参数为true后,对象参数不是简单的合并了,它会判断具体是哪里不一样,最后返回一个完整的对象(一般这才是我们想要的)。想写这篇文章也是从这插件的源码有感而来
那么利用Object.assign怎么实现该效果呢
刚写了个:
https://github.com/Newbit13/pika/blob/master/trueAssign.js
没事赞一下呗。

再附上一篇文章,lodash没怎么用过,所以给大家看看就好Lodash 中 assign,extend 和 merge 的区别

xhr.onload和xhr.onreadystatechange

一个关系不是很大的有趣链接:理解formdata,Blob等数据类型

我在这文章里看到张哥关于ajax的xhr.onload的写法,想起我们以前不是又得onreadystatechange,又得readystate,
所以产生了疑问:xhr.onloadxhr.onreadystatechange效果一样吗?
Stack Overflow的高票回答:Is onload equal to readyState==4 in XMLHttpRequest?
答案:这是xhr2才有的,如果浏览器支持就用,一样的。虽然说不是高票回答就是真理,但心理看着踏实是肯定的。。。

另外:Stack Overflow打开缓慢不是服务器太远的原因,跟墙有关。但墙的不是它,是它引用了谷歌下的jq。。。火狐有插件可以让他禁止加载这些不能加载的东西。哎,哎,哎。

完。

有趣的this,对与编译器的一些猜想

话不多少,上马

    var a=1;    
    var obj={
        a:2,
        ga:function(){
            return this.a
        }
    }
    console.log((obj.ga=obj.ga)());//1
    console.log((obj.ga)());//2
    console.log((b=obj.ga)());//1

根据8跟10行,我只能斗胆猜测:
编译器为了省事,直接利用obj.ga得到的值进行xx.()这种函数调用,导致不管谁调用this指向都是全局的this。。。

挖个坑吧,我很想被打脸的。
完。

ES6的箭头函数this指向

参考ES6 箭头函数中的 this?你可能想多了(翻译)
ES6的箭头函数的this指向我认为所在的作用域属于谁就指向谁

        b={
            c:{
                d:function(){
                    var e = ()=>{
                        console.log(this);//打印c
                    }
                    e()
                }
            }
        }
        b.c.d();
    /******************************************************/
        b={
            c:function(){
                var e = ()=>{
                console.log(this);//打印b
                }
                e()
            }
        }
        b.c();
/******************************************************/
        b={
            c:()=>{
                console.log(this);//打印window
            }
        }
        b.c();

完。

关于jQuery的remove和clone等需要注意的地方

jquery的remove这个api与detach的区别文档中的解释是:前者不仅删除元素,还把其属性删除。后者也是删除,但保留绑定在元素上的事件,属性这些。
就绑定事件这一项来说:
第一次,我用js的.onclick给元素a加了个事件,用jq的remove删了再加回去,发现没效啊!事件还在。
第二次,刷新,用jq的click给元素a加事件,再同样的一番操作,嗯,事件没有了。
结论:这里有个坑!remove清除的是用jq加的事件,用js加的没有清掉。
所以引出了我的一个猜想加模糊的印象:jq加事件是把事件放在一个队列里,用时去取,而不是简单的用js的实现方法代替。
猜想对不对呢?跟我哪天看看源码再回来回答这个问题,挖坑要紧!