转载:https://blog.csdn.net/weixin_34179968/article/details/88002844
一:数据存储与赋值:
1:基本数据类型在栈中存储变量名和值。
null和undefined,
都是数据类型,undefined表示未定义,有且仅有一个值,就是undefined,
null:表示空对象,typeof结果是object,和对象挂钩用null
2:引用数据类型在栈中存储变量名和在堆中存储的地址编号。
引用类型就是对象包括:内置对象(String,boolean,Date,RegExp,Math).宿主对象(bom,dom),自定义对象
dom2:bom:浏览器对象模型,有window对象,window对象默认就存在的,
dom:文档对象模型,
事件委托:
- html
- css
- js
var ul=document.getElementById('ul');
ul.οnclick=function(e){
console.log(e.target.innerHTML)
}
dom2级注册事件和解除事件从ie9开始支持,
二: 原型和原型链:
原型:每一个对象都有一个proto,每一个函数都有一个prototype,函数也是对象,所以也有proto,
原型属性:隐士原型对象上的属性
原型链:js每一个对象都有一个prototype属性,指向他的原型对象,原型对象还有自己的原型,原型一环扣一环,直到某个对象的原型为null,这一级一级的链结构obj.proto.proto就是原型链。
访问一个对象的属性时(obj.name),先从自由属性中找,如果没,就从隐式原型(obj.proto)找,一直找,直到找到null,结束,找的过程形成的链条称为原
链。
对象的隐式原型对象proto===创建这个对象的构造器的prototype,这个对象的构造器的proto===object;Object的proto__为null.
var arr=[] arr.__proto__===Array.prototype var obj={} obj.__proto__===Object.prototype function fn(){} fn.__proto__===Function.prototype
三:对象与数组:对象:是属性的集合,分自有属性,原型属性:隐式原型对象上的属性
var obj={
name:"js",
more:'node'
}
console.log(obj.name);//或 obj['name'] //访问
delete obj.name //删除属性,属性的configurable必须为true
for(var p in obj){
console.log(obj[p]); //遍历
}
obj.hasOwnProperty(name);//判断是否有某个自有属性,
数组:批量定义数据。
数组的方法:join():将数组以某种符号连接变成字符串,
reverse():将数组中元素倒置
concat():将两个数组练成一个数组,
sort():排序
slice():截取数组长度,包头不包尾
splice():添加删除于一体。
push,pop,shift,unshift
数组去重: var aa=[1,3,5,4,3,3,1,4]
function arr(arr) {
var result=[]
for(var i=0; i<arr.length; i++){
if(result.indexOf(arr[i])==-1){ //没有返回-1
result.push(arr[i])
}
}
console.log(result)
}
arr(aa);
统计各个元素出现的个数:
var aa=[1,3,5,4,3,3,1,4] // console.log(aa.indexOf(89)); //没有则为-1 function count(arr){ var obj={}; for(var i=0;i<arr.length;i++){ if(obj.hasOwnProperty(arr[i])){ obj[arr[i]]=obj[arr[i]]+1; }else{ obj[arr[i]]=1; } } return obj; } 字符串:方法,concat:字符串连接, charAt():获取指定索引的字符 indexof():获取指定字符的索引,从左到右,找到第一个, lastindexof():获取指定字符的索引从右到左,找到第一个 splice():截取 toUpperCase(),toLowerCase()大小写转换 replace():替换复制代码
四:闭包定义:在函数的外部可以访问函数内部的变量。
闭包会延长变量的生命周期,
1:function a(){ var i=1; function b(){ console.log(i); } return b; } var f=a(); f();//2 i没被回收 f();//3
var lis=document.getElementsByTagName('li'); for(var i=0;i<lis.lenght;i++){ lis[i].οnclick=(function(index){ return function(){ console.info(index); } })(i); };
五:this的指向
1:在函数内部this永远都指向window对象,在函数外部也指向window
function fn(){ function fn2(){ console.log(this); } fn2(); }; fn(); //window 立即执行函数中: (function (){ "use strict" console.log(this) })() //undefined 避免污染全局
2:全局执行 console.log(this) //window node环境下指向global 严格模式node环境下:this 为undefined 2:在对象的方法中,指向当前对象 var obj={ name:'js', write:function(){ console.log(this.name); } } }或者 var obj={ name:'js', write:fn } function fn(){ console.log(this.name) } obj.write(); //js 把对象的方法赋值给一个变量,调用这个变量时,指向window var f=obj.write; f() //window 回调函数中的this var obj={ name:'js', foo0:function(){ console.log(this) }, foo:function(){ console.log(this); setTimeout(this.foo0,1000) //window 对象 } } obj.foo() 3:通过new创建的函数,会指向当前对象 function F(){ console.log(this); }; var f=new F(); console.log(f); 4:出现在对象的事件函数中,会指向当前对象 <button οnclick="add(this)">点击</button> function add(value){ console.log(value);//button } 5:可以通过applay和call改变this的指向 (1)var obj={ name:'node' }; function say(){ console.log(this); console.log(this.name); }; say.call(obj); (2)call与applay的区别,参数形式不一样 var obj={ name:'node' }; function add(x,y){ return x+y; }; var result=add.call(obj,1,2); //函数调用call, var result2=add.apply(obj,[2,3]);//函数调用apply,[]数组形式 console.log(result,result2); call和applay 六:js原型和继承: _proto_:(隐式原型):是对象内部的属性,指向另一个对象的原型 prototype:(显示原型)是函数的属性,指向函数的原型。 显式原型的作用是用来实现基于原型的继承与属性的共享。 隐式原型的作用是构成原型链,同样用于实现基于原型的继承, js的oop编程 1:生成实例对象的最原始模式 var cat={ name:'', color:'' } 改进:function Cat(name,color){ return {name:name,color:color} } 构造函数模式: function Cat(name,color){ this.name=name; this.color=color; this.type="猫类动物"; this.eat=function(){ }, this.say=function(){} } var cat1=new Cat(name,color) var cat2=new cat(name,color) cat1,cat2的costructor就是 Cat() cat1.eat==cat2.eat //false instanceof运算符:验证原型对象与实例对象之间的关系 cat instanceof Cat//true 构造函数创建的实例,每个type属性和eat方法都是重复的内容,多占用一些内存,既不环保,也缺乏效率,可以让type属性和eat方法只生成一个实例, prototype模式:每一个构造函数都有一个prototype属性,指向另一个对象,这个对象的所有属性和方法都会被构造函数的实例继承,可把那些不变的属性和方法定义在prototype对象上, function Cat(name,color){ this.name=name; this.color=color; } Cat.prototype.eat=function(){ } var cat1=new Cat(name,color) var cat2=new cat(name,color) 此时 cat1.eat==cat2.eat //true prototype模式的验证方法, isPrototypeof方法, Cat.prototype.isPrototypeOf(cat1) //true 每一个实例都有一个hasOwnPrototype()方法 判断是本地属性还是继承自prototype对象的属性 in运算符可以判断某个实例是否有某个属性,不管是不是本地属性 “name” in cat1 //true in运算符还可以遍历 浅拷贝: 深拷贝: function deepCopy(p,c){ var c=c||{}; for(var i in p){ if(typeof[i]==="object"){ c[i]=(p[i].constructor===Array)?[]:{}; deepcopy(p[i],c[i]); }else{ c[i]=p[i]; } } return c; } 七:js拖拽实现: .box{ 150px; height: 180px; border:1px solid red; position: relative; } .fangdajing{ 80px; height: 100px; background:url("./img/scope.png"); position: absolute; left:0; top:0; display: none; cursor: move; } var box=document.getElementById('box'); var fangdajing=document.getElementById('fangdajing'); var xiaotu=document.getElementById("xiaotu"); var fangdajing_left=0; var fangdajing_top=0; box.οnmοuseenter=function(){ fangdajing.style.display="block"; } box.οnmοuseοver=function(e){ fangdajing_left=fangdajing_left<0 ? 0:e.clientX-xiaotu.offsetLeft-fangdajing.offsetWidth/2; fangdajing_left=fangdajing_left> box.offsetWidth-fangdajing.offsetWidth ? box.offsetWidth-fangdajing.offsetWidth : fangdajing_left; fangdajing_top=fangdajing_top<0 ? 0:e.clientY-xiaotu.offsetTop;-fangdajing.offsetHeight/2; fangdajing_top=fangdajing_top> box.offsetHeight-fangdajing.offsetHeight ? box.offsetHeight- fangdajing.offsetHeight : fangdajing_top; fangdajing.style.left=fangdajing_left+"px"; fangdajing.style.top=fangdajing_top+"px"; } <div class="box" id="box"> <img class="" id="xiaotu" src="./img/TB1gFOyJVXXXXXLXpXXXXXXXXXX-150-118.png"/> <div class="fangdajing" id="fangdajing"></div> <div class="fangdahou"></div> </div> 八:js中的正则 1:创建正则:构造器方式 var p=new RegExp("d","mgi") 字面量:var p=/d/mgi 正则表达式的构成:界定符,原子,修饰符:mgi 2:正则的使用:test()方法:检测目标字符串是否有符合要求的字串 var p=/a/ var str="abc" console.log(p.test(str)) //true exec():把符合要求的字串找出来, console.log(p.exec(str)) //index:0 3:原子:表示一个字符 a-z,A-Z,-0-9 加上i:表示不区分大小写复制代码
js性能优化,
1:定义局部变量
js搜索引擎在局部作用域链中搜索的深度越大,操作也会消耗更多的事件,
例:var d1=document.getElementById('d1'),d2=document.getElementById('d2');
改为:var d=document;
var d1=d.getElementById('d1'),d2=d.getElementById('d2')
2:能不使用闭包,就不使用
3:对象属性和数组元素的速度比变量慢,
因此当多次引用一个数组中元素或对象的属性时,可以通过定义一个变量获得性能提升,firbox浏览器在优化数组时让实际性能优于变量
5:不要再数组挖的更深,嵌套多层数组操作很慢
6:遍历一个集合内的元素时,不要使用for-in循环,
因为for-in不仅遍历额外的数组项还需要更多的时间。
7:修改css类而不是样式,
因为修改css局部样式更高效,局部样式发生改变时会引为回流
8:node自动化部署
9:重构和回流:
重构:改变每个元素外观时所触发的浏览器行为,比如颜色,背景等样式发生了改变而进行的重新构造新外观的过程,重构不会引发页面的重新布局,不一定伴随着回流。
回流:指的是浏览器为了重新渲染页面的需要而进行的重新计算元素的几何大小和位置的,他的开销是非常大的,回流可以理解为渲染树需要重新进行计算,一般最好触发元素重构,避免元素回流;比如通过添加类添加css样式,而不是直接在dom上设置的,需要操作某一块元素时,最好使其脱离文档流,这样就不会引起回流了,比如设置position:absolute或fixed,或者display:none,操作结束后再显示,
10:http中的长连接短连接
短连接:建立连接,数据传输,关闭连接,建立连接,数据传输,关闭连接
长连接:建立连接,数据传输...(保持连接)..数据传输--关闭连接
11:设计模式的规则:
开闭原则:一段程序对外扩展是开发的,
共分3大类:创建型模式:单例模式,工厂模式,原型模式
结构型模式:装饰者模式,
行为型模式:观察者模式,策略模式,
12:浏览器渲染过程:dns查询,tcp连接,http请求,响应,服务器响应,客户端渲染(处理html标记并构建dom树,处理css标记并构建css树,将dom和css树合并为一个树,根据dom树来布局)。此http与https:https是在http和tcp有一层ssL层,https比http安全 http的长连接和端连接,http属于应用层协议,在传输层使用tcp协议,在网络层使用ip协议负则网络路由和寻址问题,tcp协议主要解决如何在ip层之上,可靠的传输数据包,使在网路的另一端收到发端发出的所有数据包,并且顺序与发出顺序一致,http协议是无状态的,指的是协议对于事物处理没有记忆能力,服务器不知道客户端是什么状态,打开服务器上的网页和你之前打开的无任何练习 阻塞渲染css与javascript:当 HTML 解析器(HTML Parser)被脚本阻塞时,解析器虽然会停止构建DOM,但仍会识别该脚本后面的资源,并进行预加载。默认情况下,css被认为是阻塞渲染的资源,意味着浏览器不会渲染任何已处理的内容,直至cssom构建完毕,js不仅可以查询和修改dom和cssom,cssom构建时,javascript将暂停,存在阻塞的 CSS 资源时,浏览器会延迟 JavaScript 的执行和 DOM 构建。
当浏览器遇到一个 script 标记时,DOM 构建将暂停,直至脚本完成执行。
JavaScript 可以查询和修改 DOM 与 CSSOM。
CSSOM 构建时,JavaScript 执行将暂停,直至 CSSOM 就绪。
所以,script 标签的位置很重要。实际使用时,可以遵循下面两个原则:
CSS 优先:引入顺序上,CSS 资源先于 JavaScript 资源。
JavaScript 应尽量少影响 DOM 的构建。
css:<style> p { color: red; }</style> <link rel="stylesheet" href="index.css">
这样的 link 标签(无论是否 inline)会被视为阻塞渲染的资源,浏览器会优先处理这些 CSS 资源,直至 CSSOM 构建完毕。
渲染树(Render-Tree)的关键渲染路径中,要求同时具有 DOM 和 CSSOM,之后才会构建渲染树。即,HTML 和 CSS 都是阻塞渲染的资源。HTML 显然是必需的,因为包括我们希望显示的文本在内的内容,都在 DOM 中存放,那么可以从 CSS 上想办法。<link href="index.css" rel="stylesheet"> <link href="print.css" rel="stylesheet" media="print"> <link href="other.css" rel="stylesheet" media="(min- 30em) and (orientation: landscape)">
第一个资源会加载并阻塞。
第二个资源设置了媒体类型,会加载但不会阻塞,print 声明只在打印网页时使用。
第三个资源提供了媒体查询,会在符合条件时阻塞渲染。
最容易想到的当然是精简 CSS 并尽快提供它。除此之外,还可以用媒体类型(media type)和媒体查询(media query)来解除对渲染的阻塞.
改变阻塞模式
13:事件模型:dom0级事件模型是早期的事件模型所有浏览器都支持的,<p id = 'click'>click me</p> 1: document.getElementById('click').onclick = function(event){ alert(event.target); } 2:var click = document.getElementById('click'); click.onclick = function(){ alert('you click the first function'); }; click.onclick = function(){ alert('you click the second function') }
dom0级只能注册一个同一类型的函数,注册多个会覆盖,
事件捕获和事件冒泡:ie8及以下是不支持的,
dom2级可以注册多个相同的事件类型不覆盖,在DOM2级中使用addEventListener和removeEventListener来注册和解除事件(IE8及之前版本不支持)。这种函数较之之前的方法好处是一个dom对象可以注册多个相同类型的事件,不会发生事件的覆盖,会依次的执行各个事件函数。
14:1: touchslider插件实现轮播图
.focus{ 320px; height:150px; margin:0 auto; position:relative; overflow:hidden; } .focus .hd{ 100%; height:5px; position:absolute; z-index:1; bottom:0; text-align:center; } .focus .hd ul{ overflow:hidden; display:-moz-box; display:-webkit-box; display:box; height:5px; background-color:rgba(51,51,51,0.5); } .focus .hd ul li{ -moz-box-flex:1; -webkit-box-flex:1; box-flex:1; } .focus .hd ul .on{ background:#FF4000; } .focus .bd{ position:relative; z-index:0; } .focus .bd li img{ 100%; height:150px; } .focus .bd li a{ -webkit-tap-highlight-color:rgba(0, 0, 0, 0); } header{ margin-top:45px; } .focus{ 100%; height:auto; } .focus .bd li img{ height:auto; } .focus .hd{ auto; height:8px; left:50%; -webkit-transform:translateX(-50%); /*translate中的百分数是相对于自身的*/ -moz-transform:translateX(-50%); -ms-transform:translateX(-50%); -o-transform:translateX(-50%); transform:translateX(-50%); bottom:4px; } .focus .hd ul{ height:8px; background: none; } .focus .hd ul li{ 8px; height: 8px; -webkit-border-radius:50%; -ms-border-radius:50%; -moz-border-radius:50%; -o-border-radius:50%; border-radius:50%; background-color: rgba(255, 255, 255, 0.6); margin:0 5px; font-size: 0; } .focus .hd ul .on{ background-color: #099fde; } <header> <div id="focus" class="focus"> <div class="hd"> <ul></ul> </div> <div class="bd"> <ul> <li><a href="#"><img src="images/1.jpg" /></a></li> <li><a href="#"><img src="images/2.jpg" /></a></li> <li><a href="#"><img src="images/3.jpg" /></a></li> <li><a href="#"><img src="images/4.jpg" /></a></li> </ul> </div> </div> <script type="text/javascript"> TouchSlide({ slideCell:"#focus", titCell:".hd ul", //开启自动分页 autoPage:true ,此时设置 titCell 为导航元素包裹层 mainCell:".bd ul", effect:"leftLoop", autoPlay:true,//自动播放 autoPage:true //自动分页 }); </script> </header>
2:swiper插件http://www.swiper.com.cn/download/index.html复制代码