函数防抖与函数节流

此两种函数在平常的开发中不一定会遇到,但确实面试时经常遇到的问题,所以作为一名前端工程师还是需要掌握的。 1. 函数防抖 在用户注册时验证用户名是否被占用,很多网站为了提升用户体验,不再等待用户点击提交按钮才去校验输入内容,而是输入框有输入内容时就校验。但是这样实现会增加浏览器请求服务器的压力,所以此时函数防抖就派上用场了。函数防抖:顾名思义,就是等一系列输入操作都完成之后,一段时间内没有输入动作,再去请求服务器进行校验。具体实现如下: 1 2 3 4 5 6 7 8 9 10 11 12 var timer = null; // 此处一定要是全局变量,至少不能在每次调用deb Continue reading

动态引入require,import

动态引入require,import 本篇基于图片加载的基础来简单介绍require, require.context和import的区别! 现如今的前端项目用webpack打包已经成为了行业趋势,然而在此模式的前提下,图片的引入是我们不可避免的问题。正常的图片引入是用img标签或者元素背景图的方式,采用这种方式的图片,webpack都能正常打包并显示。但是如果直接在js文件中定义图片路径,并赋给图片元素的话不能正常显示的,这是因为webpack打包后,会将静态资源文件放在dist/static/img下,我们的网站实际上以dist目录作为根目录,并由此加载该目录下的index.html所 Continue reading

JavaScript同步与异步

1. 定义 JavaScript是一个单线程的语言,就像一条流水线,但也仅仅是一条流水线,不能同时进行多个任务和流程。它之所以是单线程,与它的用途有关,作为浏览器的脚本语言,JavaScript的主要用途是与用户互动,以及操作DOM,这决定了它只能是单线程的,否则会带来很复杂的同步问题。 所谓同步和异步做事情的时候都是只有一条流水线,同步和异步的差别就在于这条流水线上各个流程的执行顺序不同。 所有任务可以分成两种,同步和异步: * 同步任务(synchronous):在主线程上排队执行的任务,只有前一个任务执行完毕,才能执行后一个任务。 * 异步任务(asynchronous):不 Continue reading

前端中的安全攻防

1. sql 脚本注入 所谓SQL注入式攻击,就是攻击者把SQL命令插入到Web表单的输入域或页面请求的查询字符串,欺骗服务器执行恶意的SQL命令。攻击者通过在应用程序预先定义好的SQL语句结尾加上额外的SQL语句元素,欺骗数据库服务器执行非授权的查询,篡改命令。 1. URL地址防注入 1 2 3 4 5 6 7 8 9 //过滤URL非法SQL字符 var sUrl=location.search.toLowerCase(); var sQuery=sUrl.substring(sUrl.indexOf("=")+1); re=/select|update|delete|tru Continue reading

http-https

HTTP HTTPS http&https释义 HTTP(Hyper Text Transfer Protocol)超文本传输协议,是一种建立在TCP上的无状态连接。用来在计算机世界里传输文字,图片,音频,视频等超文本数据的约定和规范。 HTTPS(Hyper Text Transfer Protocol Secure)安全的超文本传输协议,它是基于HTTP+TLS/SSL实现的,可以说是披上了一层TLS/SSL的HTTP协议。 TCP/IP网络模型 常见的TCP/IP网络模型为5层模型: 也可以分为四层,即把数据链路层和物理层统一表示为网络接口层。 还有一种是OSI七层网络模型 Continue reading

for循环中的setTimeout

1. 错误示例 1 2 3 4 5 6 7 function print() { for (var i = 0; i < 10; i++) { setTimeout(() => { console.log(i); }, 1000); } } 上面的代码,我们期望每隔一秒,输出一个数,而且这个数是每次循环i的值。但是期望也只是期望,实际情况是一秒钟之后直接输出了10个10。那么问题就来了,我们怎么实现我们的期望值呢? 由此我们先来尝试几种解决方案,并作一一对比: * 每隔一秒输出一个10 1 2 3 Continue reading

简单实现一个EventEmitter

EventEmitter 是 NodeJS 的核心模块 events 中的类,用于对 NodeJS 中的事件进行统一管理,用 events 特定的 API 对事件进行添加、触发和移除等等,核心方法的模式类似于发布订阅 1. Node 中的 EventEmitter EventEmitter本质上是一个观察者模式的实现。 观察者模式:它定义了对象间的一种一对多的关系,让多个观察者对象同时监听某一个主题对象,当一个对象发生改变时,所有依赖于它的对象都将得到通知。 1 2 3 4 5 6 7 8 9 // Node 中的 EventEmitter 简单用法 let events = r Continue reading

偏函数与函数柯里化

偏函数与函数柯里化 1. 偏函数 所谓偏函数,就是固定一个函数的一个或者多个参数,返回一个新的函数,这个函数用于接受剩余的参数。 1. 工厂方法 首先来看一个简单的例子: 1 2 3 4 5 6 7 8 9 function add (a, b) { return a + b; } add(1, 2); add(1, 3); add(1, 4); add(1, 5); add(1, 6); 我们发现,调用 add 方法时,第一个参数相同,但是我们写了5遍,鉴于此种情况,我们可以将 add 方法封装成偏函数的形式来实现更加简洁的代码。 1 2 3 4 5 6 7 Continue reading

Object的那些函数

在JavaScript中,万物皆对象! 1. 原型方法 其中,constructor, toString, toLocalString, valueOf方法是Object原型的原始方法,鉴于万物皆对象的原则,所以在JavaScript中的其他类型都会存在着几种属性。 1. constructor 原型对象有一个constructor属性,指向该原型对象对应的构造函数。 1 Object.prototype.constructor === Object; // true 1. toString() toString() 用来返回对象的字符串表示,如果此方法在自 Continue reading

正则巴啦啦

正则表达式描述了一中字符串匹配模式,可以用来检查一个串是否含有某种子串,将匹配的子串替换或者从某个串中取出某个条件的子串等。 1. 创建一个正则表达式 1. 使用一个正则字面量,其由包含在斜杠之间的模式组成: 1 2 let reg = /ab+c/; let reg = /^[a-zA-Z]+[0-9]*\W?_$/gi; 2. 使用RegExp对象的构造函数: 1 2 3 let reg = new RegExp("ab+c"); let reg = new RegExp(/^[a-zA-Z]+[0-9]*\W?_$/ ,"gi"); let reg = new Continue reading

编写可维护的JavaScript-事件处理

在所有JavaScript应用中事件处理都是非常重要的。所有的JavaScript均通过事件绑定到UI上。 很多开发者都很了解,当事件触发时,事件对象(event对象)会作为回调参数传入事件处理程序中。event对象包含所有和事件相关的信息,包括事件的宿主以及其他和事件类型相关的数据。鼠标事件会将其位置信息暴露的event对象上,键盘事件会将按键信息暴露在event对象上,触屏事件会将触摸位置和持续事件暴露在event对象上,只有提供了所有这些信息,UI才会正确地执行交互。 1 2 3 4 5 6 7 8 9 // 不好的写法 function handleClick(event) { Continue reading

JavaScript高级程序设计-事件

JavaScript与HTML之间的交互是通过事件实现的。事件最早是在 IE3 和 Netscape Navigator 2 中出现的,当时是作为分担服务器运算负载的一种手段,在 IE4 和 Navigator 4 发布时,这两种浏览器都提供了相似但不相同的API,这些API并存经过了好几个主要版本。 DOM2 级规范开始尝试一种符合逻辑的方式来标准化 DOM 事件。目前 IE9, Firefox, Opera, Safari, Chrome 全都已经实现了 DOM2 级事件模块的核心部分。 1. 事件流 试想,在页面上点击一个元素,那么不能简单的认为,仅仅点击了这个元素。在点击这个元 Continue reading

JavaScript高级程序设计-面向对象

面向对象的语言都有一个标志,那就是它们都有类的概念,而通过类可以创建任意多个具有相同属性和方法的对象。但是ECMAScript中没有类的概念,因此它的对象也与基于类的语言中的对象有所不同。 创建对象 1. 新建对象实例 通过new一个对象实例: 1 2 3 4 5 6 7 var person = new Object(); person.name = 'andy'; person.age = 29; person.sayName = function () { alert(this.name); } 2. 对象字面量 通过对象字面量的方式: 1 2 3 4 Continue reading

编写可维护的JavaScript-变量函数和运算符

JavaScript编程的本质是编写一个个的函数来完成任务。 1. 变量声明 变量声明都是通过var语句来完成的。JavaScript中允许多次且在任何地方使用var语句,这对开发者来说是很有意思的一件事情,因为不论var语句是否真的会被执行,所有的var语句都提前到包含这段逻辑的函数的顶部执行,比如: 1 2 3 4 5 function doSomething () { var result = 10 + value; var value = 10; return result; } 在这段代码中,变量value在声明之前就参与了运算,这是完全合法的 Continue reading

编写可维护的JavaScript-全局变量

JavaScript执行环境在很多方面都有其独特之处。全局变量和函数的使用便是其中之一。事实上,JavaScript的初始执行环境是由多种多样的全局变量所定义的,这些全局变量在脚本环境创建之初就已经存在了。这些都是挂载在全局对象上的。 在浏览器中,window对象往往重载并等同于全局对象,因此任何在全局作用域中声明的变量和函数都是window对象的属性,如下所示,两者都是window对象的属性。 1 2 3 4 5 6 7 8 var color = 'red'; function showColor () { alert(color); } console.log(wi Continue reading

编写可维护的JavaScript-UI层的松耦合

在web开发中,用户界面中是由三个彼此隔离又相互作用的层定义的: * HTML用来定义页面的数据和语义。 * CSS用来给页面添加样式,创建视觉特征。 * JavaScript用来给页面添加行为,使其更具交互性。 很多设计模式就是为了解决紧耦合的问题。如果两个组件耦合太紧,则说明一个组件和另一个组件直接相关,这样的话,如果修改一个组件的逻辑,那么另外一个组件的逻辑也要修改,这是很致命的。 当你做到修改一个组件而不需要更改其他的组件时,就做到了松耦合。对于多人大型系统来说,有很多人参与维护代码,松耦合对于代码可维护性来说至关重要。 需要注意的是:在一起工作的额组件无法达到“无耦合” Continue reading

编写可维护的JavaScript-基本的格式化

1. 缩进层级 坚持使用适度的缩进是万里长征的第一步,可增加代码的可读性。但是对于大多数变成风格来说,代码到底应该如何缩进并没有统一的共识,有以下两种主张。 a. 使用制表符进行缩进 一个缩进层级用一个制表符来表示,两个缩进层级用两个制表符,以此类推。这种方法的好处是:第一,缩进层级与制表符之间一一对应,符合逻辑。第二,文本编辑器可以配置制表符的展现长度,表现出不同的代码风格。但是这种方式的主要缺点是,系统对制表符的理解不一致。所以会出现在一个系统用一个编辑器打开的代码与另一个系统用相同的编辑器打开的代码展现效果不一样。这对于那些追求代码一致性的团队来说是一个很难受的东西。 b. Continue reading

编写可维护的JavaScript-注释

注释是代码中最常见的组成部分,他们是另一种形式的文档,也是很重要的一部分。 JavaScript支持两种不同类型的注释:单行注释和多行注释。 1. 单行注释 1 // 这是一个单行注释 很多人喜欢在双斜线后敲入一个空格,用来让注释文本有一定的偏移,当行注释有三种使用方法。 * 独占一行的注释,用来解释下一行代码。这时注释之前总有一个空格,且缩进层级和下一行代码保持一致。 * 在代码行的尾部的注释。代码结束到注释之间至少有一个缩进。注释(包括之前的代码部分)不应当超过单行最大字符数限制,如果超过了,就讲这条注释放置于当前代码行的上方。 * 被注释掉的大段代码(很多编辑器都 Continue reading

不同设备的click

不同设备的Click 1. onclick是绑定事件,click是方法 click本身是方法作用是触发onclick事件,只要执行了元素的click()方法,就会触发onclick事件。 1 2 3 $("#btn1").click(function(){ $("#btn2").click(); }); 2. click与tap click为了能区分单击与双击在每次点击之后加了300ms的延迟,但是这种延迟会造成反应迟钝的感觉。为了解决这一问题,可以使用zepto的tap事件,singleTap和doubleTap 分别代表单次点击和双次点击。在使用zepto框架的 Continue reading