赞
踩
jpg:有损压缩,体积较小,不支持透明,不支持动画
png:采用有损压缩法,体积相对较小,支持透明背景色,不支持动画
gif:支持动画,只有全透明和不透明两种,只有256种颜色
svg:一般会保存颜色及形状嫌贵简单的图片,可任意放大图片显示,边缘异常清晰
bmp:无损压缩格式,画质最好,文件太大,不利于网络传输
1、盒模型:元素所占网页空间的大小:元素内容(content)、内边距(padding)、边框(border)、外边距(margin)
2、两个上下方向相邻的元素框垂直相遇时,外边距会合并,合并后的外边距的高度等于两个发生合并的外边距中较高的那个边距值
1、标准盒模型 box-sizing:content-box
总宽 = width+padding的左右+border的左右+margin左右
2、怪异(ie)盒模型 box-sizing:border-box;/ 在低版本ie不写文档类型声明也会触发
总宽 = width(已经包含了内容区+padding+边框) + margin左右
3、虽然怪异盒模型属性,会让添加了padding和boder的盒子不会变大,但同时却 让该盒子的内容区变小,所以有时候添加怪异盒模型属性时,还要考虑到该盒子所包含的内容
音频引入:<audio src="音频地址3" controls autoplay loop muted></audio>
属性:
src: 音频路径
controls: 控件
loop:循环
muted: 静音
autoplay: 自动播放,谷歌浏览器禁止了
video视频 常见格式 ogv/mp4/webm
视频引入: <video src="视频地址" controls height="300" autoplay loop muted></video>
属性:
object-fit: cover;让视频全屏显示
src: 音频路径
controls: 控件
loop:循环
muted: 静音
autoplay: 自动播放 静音后可以自动播放
poster: 视频未播放之前的视频封面
h5原有语法:
DOCTYPE 可以使用小写
单标签没有结束标签
可以省略结束的标签:li、dt、dd、p、option、colgroup(用于对表格中的列进行组合)、thead、tbody、tfoot、tr、td、th
可以省略的标签:html head body tbody
新增标签语法:语义化,ie8及以下不生效
header 标签头部
section 划分板块
article 与上下文无关的内容
aside 可以放侧边工具栏
nav 导航
figure和figcaption 图文共存
footer 底部
main 比较重要的部分
mark 标记默认是黄色的高亮,可以修改样式内联
audio音频 常见格式 mp3
video视频 常见格式 ogv/mp4/webm
表单新增type类型:
type=“email” 限制用户必须输入email类型
type=“url” 限制用户必须输入url类
type=“range” 产生一个滑动条表单
type=“number” 限制用户必须输入数字类型
type=“search” 产生一个搜索意义的表单
type=“color” 生成一个颜色选择的表单
type=“time” 限制用户必须输入时间类型
type=“week” 限制用户必须输入周类型
type=“datetime-local” 选取本地时间
type=”date”
表单新增属性:
required 必填。
min 最小 在type=“number”使用
max 最大 在type=“number”使用
autocomplete 是否自动提示信息 属性值 on off/结合name和value和后台使用
placeholder 文本框的提示信息
autofocus 自动聚焦。一个页面只能由一个。
pattern 后面的属性值是一个正则表达式。 pattern="[A-z]"
novalidate 取消所有的表单验证 加在form身上
multiple 选择(上传)多个 加在type="file"里面
CSS3 相比 CSS2 对边框、背景、渐变、文本效果、字体、转换效果、过渡、动画、图片、用户界面、盒模型、媒体查询等都有了很大的改进,新增了不少功能和属性
边框:
1、盒子边框属性
border-radius
box-shadow
border-image
1、border-radius 圆角 border-radius:50%/100%(画圆) 2、box-shadow 盒子阴影 box-shadow:水平偏移 垂直偏移 模糊程度色 模糊大小(可省略) 位置(inset); 3、border-image 指定一个图片作为边框 border-image:图片url 图片边界向内偏移 图像边界的宽度(默认为边框的宽度) 用于指定在边框外部绘制偏移的量(默认0) 铺满方式--重复(repeat)、拉伸(stretch) 或 铺满(round) (默认拉伸)vv
背景:
1、盒子背景属性
background-image
background-size
background-origin
background-clip
1、background-image 通过该属性给盒子添加背景图 background-image:url,定位(right bottom),平铺(no-repeat) background-position:水平(10px) 垂直(数值px); 2、background-size 背景图大小 background-size:宽度(10px) 高度(数值px); // 宽高可以是像素值,也可以是百分比 3、background-origin 背景图像的起始位置(原点) background-origin:content-box/padding-box/border-box//三个属性三选一,区域内可以放置背景图像 4、background-clip 从content-box, padding-box,或 border-box位置进行背景图像裁剪 background-clip:content-box/padding-box/border-box //三个属性三选一,区域内可以防止背景图像 背景图复合写法background: 颜色 路径 重复 位置(0px 0px)/大小
渐变:
(gradients)可以让你在两个或多个指定的颜色之间显示平稳的过渡
线性渐变(linear-gradient)- 向下/向上/向左/向右/对角方向
径向渐变(Radial Gradients)- 由它们的中心定义
1、线性渐变: background-image/background:linear-gradient(方向,颜色1,颜色2……) 渐变方向: to bottom 向下 to right 向右 to top 向上 to left 向左 to right bottom 向右下角 to left top 向左上角 to right top 向右上角 to left bottom 向左下角 数值+deg(角度) background: linear-gradient(red 40%, blue 60%); //0%-40% 是红色的纯色 40%-60% 红色到蓝色渐变 60%-100% ;蓝色的纯色 2、重复性的线性渐变 background:repeating-linear-gradient(red 40%, blue 60%); 3、径向渐变 bakrgound-image/background:radial-gradient(位置,颜色1,颜色2..) background:radial-gradient(center,shape,size,颜色1,颜色2..) //渐变的中心,形状(圆形circle或椭圆型ellipse),大小 位置: center 中心 水平方向:left/center/right 垂直方向:top/center/bottom 兼容写法: background: radial-gradient(left, red, blue); background: -webkit-radial-gradient(left, red, blue); background: - ms-radial-gradient(left, red, blue); 4、重复性的径向渐变 background: repeating-radial-gradient(red 20%, yellow 40%);
文本效果:
文本新增属性:
text-shadow
box-shadow
text-overflow
word-wrap
word-break
1、text-shadow 给文字添加阴影 text-shadow:水平阴影5px 垂直阴影5px 模糊距离5px 阴影的颜色#F0000 2、box-shadow 给盒子添加阴影 box-shadow:X轴偏移10px y轴偏移10px 模糊距离5px 阴影颜色yellow 3、text-overflow 展示溢出内容效果 text-overflow:clip / ellipsis / string clip: 修剪文本 ellipsis:显示省略符号来代表被修剪的文本 string:使用给定的字符串来代表被修剪的文本 4、word-wrap 自动换行属性允许您强制文本换行 word-wrap:normal / break-word normal:只在允许的断字点换行(浏览器保持默认处理) break-word:允许长文本换行,在长单词或 URL 地址内部进行换行 5、word-break 单词拆分行 指定换行规则 word-break:normal / break-all / keep-all normal:使用浏览器默认的换行规则 break-all:允许在单词内换行 keep-all:只能在半角空格或连字符处换行
css3其它文本属性
字体:
@font-face通过CSS3,web利用该属性来设置自己喜欢的字体
//在新的 @font-face 规则中,您必须首先定义字体的名称(比如 myFirstFont),然后指向该字体文件 @font-face { font-family:myFirstFont //字体的名字 src:url() //定义字体文件的url }
2D转换:
可以移动,比例化,反过来,旋转,和拉伸元素
1、属性
transform
transform-origin
2、方法
translate()
rotate()
scale()
skew()
matrix()
1、translate() 移动 transform:translate(x轴移动的距离50px,y轴移动的距离100px) //原点在左上角 2、rotate() 旋转,旋转过后,原点会跟着变化,负值是允许的,这样是元素逆时针旋转 transform:rotate(旋转角度30deg) //元素顺时针旋转30度 CSS3 允许您使用 3D 转换来对元素进行格式化: (rotateX()方法,围绕其在一个给定度数X轴旋转的元素 rotateY()方法,围绕其在一个给定度数Y轴旋转的元素) 3、scale() 缩放 transform:scale(宽度的倍数2,高度的倍数4) 4、skew() 倾斜 transform:skew(相对于x轴角度30deg,相对于y轴角度20deg) 5、matrix() 矩阵 transform:matrix(旋转角度,缩放比例,移动,倾斜)
过渡:从一种样式转变到另一个
属性 | 功能 | CSS |
简写属性,用于在一个属性中设置四个过渡属性。 | 33 | |
transition-property指定需要变化的属性 | 规定应用过渡的 CSS 属性的名称。 | 3 |
定义过渡效果花费的时间。默认是 0。 | 3 | |
规定过渡效果的时间曲线。默认是 “ease”。 | 3 | |
transition-delay延迟执行时间 | 规定过渡效果何时开始。默认是 0。 | 3 |
transition:指定需要变化的属性width,完成时间1s,转速曲线liner,延迟执行时间1s
动画:我们可以创建动画,它可以取代许多网页动画图像
1、属性:
@keyframes: 定义一个动画
animation: 去执行这个动画
@keyframes 动画名myfirst { from{background:red;} to{background:yellow;} } //或者以百分比指定动画发生时间 @keyframes 动画名myfirst { 0% {background:red;} 25% {background:blue;} 50% {background:pink;} 100% {background:yellow;} } //改变背景色和位置 @keyframes 动画名myfirst { 0% {background:red; left:0px; top:0px;} 25% {background:blue; left:200px; top:0px;} 50% {background:pink; left:200px; top:200px;} 75% {background:pink; left:0px; top:200px;} 100% {background:yellow; left:0px; top:0px;} }
下面的表格列出了 @keyframes 规则和所有动画属性:
属性 | 功能 | css |
@keyframes | 规定动画 | 3 |
animation | (动画名动画持续时间延迟时间动画效果执行次数)所有动画属性的简写属性,除了 animation-play-state 属性 | 3 |
animation-name : myfirst | 规定 @keyframes 动画的名称 | 3 |
animation-duration: 5s | (动画的持续时间 s/ms)规定动画完成一个周期所花费的秒或毫秒。默认是 0 | 3 |
animation-timing-function : linear(匀速)/ease:逐渐慢下来 /ease-in:加速/ease-out:减速/ease-in-out先加速后减速 | (动画的效果)规定动画的速度曲线。默认是 “ease” | 3 |
animation-delay:2s | (过渡延迟时间 s(秒)/ms(毫秒)规定动画何时开始。默认是 0 | 3 |
animation-iteration-count:infinite(无限循环)/具体的数值 | 规定动画被播放的次数。默认是 1。 | 3 |
animation-direction:alternate(正向和反向交替运动)/normal 正向/reverse 反向 | (动画执行的方向)规定动画是否在下一周期逆向地播放。默认是 “normal” | 3 |
animation-play-state:runing(播放默认值)/paused 暂停 | 规定动画是否正在运行或暂停。默认是 “running” | 3 |
//使用动画 div{ animation:myfirst 5s //简写:animation:myfirst 5s linear 2s infinite alternate }
弹性盒子:弹性布局
resize
box-sizing
outline-offset
resize 用户是否可以调整盒子的大小 resize:none用户无法调整元素的尺寸/both用户可调整元素的高度和宽度/horizontal用户可调整元素的宽度/vertical用户可调整元素的高度 box-sizing 确定盒子的宽高都包含什么 box-sizing:content-box/border-box/inherit outline-offset 在盒子的边框border外面在加一层轮廓 outline-offset:length轮廓与边框边缘的距离/inherit规定应从父元素继承 outline-offset 属性的值
值 | 含义 |
content-box | 这是CSS2.1指定的宽度和高度的行为。指定元素的宽度和高度(最小/最大属性)适用于box的宽度和高度。元素的填充和边框布局和绘制指定宽度和高度除外 |
border-box | 指定宽度和高度(最小/最大属性)确定元素边框box。也就是说,对元素指定宽度和高度包括padding和border的指定。内容的宽度和高度减去各自双方该边框和填充的宽度从指定的"宽度"和"高度"属性计算 |
inherit | 指定box-sizing属性的值,应该从父元素继承 |
媒体查询
用来做响应式布局开发
属性:@media
//媒体指:不同的设备 //查 询:检测属于哪种设备,实现页面在不同的设备下正常预览 //媒体特性:用来描述设备的特点:宽、高..... //将媒体类型和媒体特性链接到一块,进行设备检测 <style> body{ background-color:pink; } // @media 媒体类型 and(条件){} @media screen and(max-width:960px){ body{ background-color:red; } } @media screen and(max-width:500px){ body{ background-color:back; } } <style/> <body> <h1>重置浏览器窗口查看效果 <h1/> <p>如果媒体类型屏幕的可视窗口宽度小于960px,背景颜色将改变 <p/> <p>如果媒体类型屏幕的可视窗口宽度小于500px,背景颜色将改变 <p/> <body/>
css3 选择器
属性选择器
[属性名] 可以选择到官方或者自定义的属性
[属性名="属性值"] 匹配属性值
[属性名~=""] 包含该值必须单独出现的
[属性名*=""] 只要包含该值就行
[属性名^=""] 以该值开头
[属性名$=""] 以该值结尾
伪类选择器
结构性伪类选择器(child 系列)
1.E:first-child E 必须是父元素里面的第一个孩子
2.E:last-child E 必须是父元素里面的最后一个孩子
3.E:**nth-child(n)** 不匹配前面的元素类型,如果对应的位置是该元素才匹
配
4. E:only-child 必须只有他自己一个孩子
结构性的伪类选择(type 系列)
1.E:first-of-type 匹配到该元素中的第一个孩子
2.E:last-of-type 匹配到该元素的最后一个孩子
3.E:**nth-of-type(n)** 匹配到该元素的第几个孩子 n 可以是表达式 2n 3n
2n+1 even(偶数) odd(奇数)
4.E:nth-last-of-type(n) 匹配到该元素的倒数第几个
目标伪类:结合锚点使用
状态伪类选择器
1.:enabled 元素可编辑
2.:disabled 元素不可编辑
3.:checked 选中
4.::selection 高亮状态一般修改字体颜色和背景色
动态伪类选择器
1.:link 未访问前
2.:visited 访问过后
3.:hover 鼠标滑过
4.:active 鼠标点击之后
层级选择器
后代选择器选择器选择器
子项选择器选择器>选择器
相邻的兄弟选择器+选择器紧挨着的兄弟
相邻的兄弟们选择器~选择器紧挨着的弟弟们
在一个页面上,有三个div盒子从上而下排列,如果,div1浮动,div1 就会飘起来,脱离标准流,那么就会改变div2 和div3 的位置,这两个盒子的位置就会上移,占到div1的位置,所以我们需要清除div1 浮动给div2 和div3 造成的影响,所以给被浮动影响的元素清除浮动,一般清除浮动主要是解决高估塌陷的问题
清除浮动方法:
1.clear:both 抗浮动
属性:
left:设置了该属性值的元素的盒子的左侧边不能与浮动元素相邻
right:设置了该属性值的元素的盒子的右侧边不能与浮动元素相邻
both:设置了该属性值的元素的盒子的两侧边不能与浮动元素相邻
none:默认值,允许该元素的盒子边左右两侧与浮动元素相邻
inherit:继承父元素的clear属性
优缺点:
优点:通俗易懂,方便
缺点:添加无意义标签,语义化差
2.额外标签法( 给谁清除浮动,就在其内部后面额外添加一个空白标签 ,给其设置clear:both;)(不推荐)
优缺点:
优点:通俗易懂,方便
缺点:添加无意义标签,语义化差,结构化差
3.父级添加 overflow 属性(overflow:hidden)不推荐
通过触发BFC方式,实现清除浮动
优点:代码简洁
缺点:内容增多的时候容易造成不会自动换行导致内容被隐蔽掉,无法显示要溢 出的元素
4.给父级设置高度
优点:简单,代码少,容易掌握
缺点:只适合高度固定的布局,要给出精确的高度,如果高度和父级 div 不一 样时,会产生问题
5.父级 div 定义 overflow:auto(必须定义 width 或 zoom:1,同时不能定义 height,
使用 overflow:auto 时,浏览器会自动检查浮动区域的高度)
优点:简单,代码少,浏览器支持好
缺点:内部宽高超过父级 div 时,会出现滚动条。
6.使用 after 伪元素清除浮动(推荐使用)
.fahter:after{ //伪元素是行内元素 content:""; display:block; clear:both; height:0; overflow:hidden; visibility:hidden } .fahter{ *zoom:1 //ie6-7 清除浮动的方式 }
优点:符合闭合浮动思想,结构语义化正确
缺点:ie6-7 不支持伪元素:after,使用 zoom:1
1、静态定位 position:static ,默认值
2、相对定位 position:relative
1、参考物:自己
2、相对定位不会脱离文档流,文字不能被遮挡
3、绝对定位 position: absolute(子绝父相)
1、参考物:含有定位的离得自己最近的祖先元素,如果没有,参考浏览器窗口
2、绝对定位会脱离文档流,内联元素会变块,文字会被遮挡,
4、固定定位 position:fixed;
1、参考物: 浏览器窗口
2、脱离文档流,内联元素会变块
3、给该元素加个margin-top:固定元素的高度
5、粘性定位 position:sticky;
1、参考物:浏览器窗口
2、移动方向 top; 一般设置为0
3、特点:没有达到top值之前正常显示,达到后类似于固定定位,不跟随滚动条滚动,且脱离文档流(吸顶效果)
6、锚点定位:必须有id名,必须有超链接
锚点:实现板块之间的跳转
利用超链接和id的结合
1、所有脱离文档流的元素都会有以下三个特点:
1)、内敛元素会变块
2)、margin:auto会失效
3)、脱离文档流
2、哪些属性会脱离文档流:flort(浮动)、absolute(绝对定位)、fixed(固定定位)、粘性定位fixed、弹性盒
块级格式化上下文,一块独立渲染的区域 (BFC就是页面上的一个隔离的独立容器,容器里面的子元素不会影响到外面的元素。)
BFC触发条件
(1) overflow的值为hidden/scroll/auto
(2) display的值inline-block/table-caption/table-cell/flex(弹性盒)/inline-flex(内联弹性盒)
(3) float的值为left/right
(4) position:absolute/fixed
BFC特性
(1) 在BFC区域里面浮动元素的高度会计算在内 (解决高度塌陷)
(2) BFC区域里面不会影响到BFC区域的外面 (解决margin的重叠/传递)
(3) BFC的区域不会和浮动元素重叠
形成BFC区域,会解决上面三个问题
1、定位+margin:auto (子绝父相)
父元素 position: relative
子元素 position: absolute ;left:0;top:0;right:0;bottom:0;margin: auto;
(2、内联元素/内联块元素:line-height:父元素的height、text-align:center
当子元素为单行文本,则可以设置行高,垂直居中,然后水平居中)
3、弹性盒display:flax,主轴和交叉轴的中心
父元素设置弹性盒display:flax;justify-content: center;align-items: center;
4、定位+ 元素已知宽度 (子绝父相)
父元素 position: relative
子元素 position: absolute ;left:50%px ; top:50%px ; margin-left:-子盒子宽的一半 ;margin-top:负的子盒子高的一半
(left:50%px:是指距离左边50%px; margin-left:50px , 也是距离左边50px,也就是向右移动50px)
5、定位+位移transform: translate
父元素 position: relative
子元素 position: absolut; left:50%px; top:50%px; transform:translate(-50%,-50%);
(transform: translate(x位移,y位移) 只写一个值代表x轴位移)
1、vertical-align:middle 把该元素放到父元素的中部(就是垂直居中)
当子元素属于inline(内联元素)或是inline-bloc(内联块元素)(比如:图片,按钮,单复选框,单行/多行文本框等),可以使用vertical-align属性
且当父元素是块元素,且有高:给子元素设置css属性vertical-align:middle
(2、line-height:父元素的height
当子元素为单行文本,则可以设置行高,使该元素垂直居中,)
3、弹性盒display:flax,交叉轴的中心
父元素设置弹性盒display:flax ;align-items: center;(子元素在交叉轴的位置)
3、3、弹性盒display:flax,交叉轴的中心
父元素设置弹性盒display:flax ;
子元素:align-self:center(单独调整某个子元素在交叉轴的对齐方式 )
4、定位+位移transform: translate
父元素 position: relative
子元素 position: absolut; left:50%px; top:50%px; transform:translate(-50%,-50%);
1.内联元素/内联块元素: text-align:center
2.块级元素:margin:auto
3.给父元素设置弹性盒:display:flex,justify-content:center
4.定位+位移transform: translate
1、标准盒模型 box-sizing:content-box
总宽 = width+padding的左右+border的左右+margin左右
2、怪异盒模型 box-sizing:border-box;/ 在低版本ie不写文档类型声明也会触发
总宽 = width(已经包含了内容区+padding+边框) + margin左右
虽然怪异盒模型属性,会让添加了padding和boder的盒子不会变大,但同时却会让该盒子的内容区变小,所以有时候添加怪异盒模型属性时,还要考虑到该盒子所包含的内容
谷歌浏览器默认最小字体为12px,小于12px的字体它都以12px显示
针对谷歌浏览器内核,加webkit前缀,用transform:scale( )这个属性进行缩放
<style> div{ font-size:10px; -webkit-transform:scale(0.8); //使用缩放方式使字体变小,比如以字体大小12px为基数,缩放80%就是9.6px display:bloc / inline-block //因为scale()属性只针对可以定义宽高的元素有效 } <style/>
选择器
1、基础选择器
2、伪元素选择器
选中第一个字(块级元素才生效)
::first-letter{}
选中第一行(块级元素才生效)
::first-line{}
给元素的最前面添加内容(内联元素)
::before{content:""} content必须有,没有内容也需要写 空引号
给元素的最后面添加内容(内联元素)
::after{content:""} content必须有,没有内容也需要写 空引号
结构性的伪类:父亲 孩子:nth-of-type(第几个孩子)
目标伪类 目标:target{} 结合锚点使用,跳转到该板块之后显示的样式
使用伪元素选择器:before/after 新生儿时,必须给其添加绝对定位,使其脱离文档流,可以不影响后面的元素
3、层级选择器
后代选择器----选择器 选择器
子代选择器---- 选择器>选择器 :选择到他的所有一代后代
相邻的后面的兄弟---- 选择器+选择器 :和他挨着的一个弟弟
相邻的后面的兄弟们---- 选择器~选择器; :它后面的所有弟弟
当hover过一个元素,改变另一个元素且不是他的后代,而是他的兄弟,则是p:hover+div
4、属性选择器
[属性名]{} 有该属性名的
[属性名="属性值"]{} 属性名和属性值的匹配
[属性名^="值"] 属性值以该值开头
[属性名$="值"] 属性值以该值结尾
[属性名*="值"] 属性值包含该值
继承属性
1、字体类:
1. font-family:字体类型;
2. font-weight:字体加粗;
3. font-size:字体大小
4. font-style: 字体样式
5. text-indent: 缩进(只对块级元素生效)
6. text-align:对齐方式
7. line-height:行高
8. word-spacing:字之间的距离;
9. letter-spacing:字符之间的距离;
10.text-decoration:文本修饰
2、文本类:
1. color:颜色
3、列表:
1. list-style-type:列表类型
2. list-style-image:图标路径
3. list-style-position:图标的位置
4. list-style:none;去掉列表符号
优先级:
样式优先级为就近原则
选择器优先级 !important > id > class > tag(标签选择器)
1.第一等:!important 如非特殊情况,慎用!important.
2.第二等:代表内联样式,如: style=””,权值为1000。
3.第三等:代表ID选择器,如:#content,权值为100。
4.第四等:代表类,伪类和属性选择器,如.content,权值为10。
5.第五等:代表标签选择器和伪元素选择器,如div p,权值为1。
结构性伪类选择器(child 系列)
1. E:first-child E 必须是父元素里面的第一个孩子
2. E:last-child E 必须是父元素里面的最后一个孩子
3. E:nth-child(n) 不匹配前面的元素类型,如果对应的位置是该元素才匹配
4. E:only-child 必须只有他自己一个孩子
结构性的伪类选择(type 系列)
1. E:first-of-type 匹配到该元素中的第一个孩子
2. E:last-of-type 匹配到该元素的最后一个孩子
3. E:nth-of-type(n) 匹配到该元素的第几个孩子 n 可以是表达式 2n 3n 2n+1
even(偶数) odd(奇数)
4. E:nth-last-of-type(n) 匹配到该元素的倒数第几个
目标伪类:结合锚点使用
状态伪类选择器
1. :enabled 元素可编辑
2. :disabled 元素不可编辑
3. :checked 选中
4. ::selection 高亮状态一般修改字体颜色和背景色
动态伪类选择器
1. :link 未访问前
2. :visited 访问过后
3. :hover 鼠标滑过
4. :active 鼠标点击之后
!important > id > class > tag(标签选择器)
1.第一等:!important 如非特殊情况,慎用!important.
2.第二等:代表内联样式,如: style=””,权值为1000。
3.第三等:代表ID选择器,如:#content,权值为100。
4.第四等:代表类,伪类和属性选择器,如.content,权值为10。
5.第五等:代表标签选择器和伪元素选择器,如div p,权值为1。
1、图片懒加载,在页面上的未可视区域可以添加一个滚动条事件,判断图片位置与浏览器顶端的距离与页面的距离,如果前者小于后者,优先加载
2、如果为幻灯片、相册等,可以使用图片预加载技术,将当前展示图片的前一张和后一张优先下载
3、如果图片为css 图片,可以使用 CSSsprite(精灵图),SVGsprite(精灵图),Iconfont(字体图标)(精灵图,小图标…)
4、如果图片过大,可以使用特殊编码的图片,加载时会先加载一张压缩的特别厉害的缩略图,以提高用户体验
5、如果图片展示区域小于图片的真实大小,则应该在服务器端根据业务需要先行进行图片压缩,图片压缩后大小与展示一致
6、对图片格式转换:转换成更好的图片格式(在画质可以接受的情况下达到更好的压缩比效果优势:减少图片加载流量,效果比较明显 劣势:服务器和浏览器压力增大,而且服务器需要额外的服务支持,格式转换要考虑浏览器的兼容性)
1、块级元素可以设置宽高,盒模型属性都生效,独占一行,一般作为容器:div,dl,dt,dd,ol,ul,li,(h1-h6),p,form,hr,table,tr,td
2、行内元素在同一行显示,不可以设置宽高,宽高由内容撑开,padding、margin 左 右显示准确,上下显示不准确,margin:0 auto,不生效:a,span,i,em,strong,b,u,del,s,br,sub,sup
3、内联块元素: img/input/textarealectideo/audio
浏览器解析CSS的两种模式:标准模式(strict mode)和怪异模式(quirks mode)。
标准模式:浏览器按W3C标准解析执行代码;
怪异模式:使用浏览器自己的方式解析执行代码,怪异模式就是浏览器为了兼容很早之前针对旧版本浏览器设计,并未严格遵循W3C标准而产生的一种页面渲染模式(因为不同浏览器解析执行的方式不一样,所以称之为怪异模式。)
如果存在一个完整的DOCTYPE则浏览器将会采用标准模式,如果缺失就会采用怪异模式
在W3C标准出来之前,不同的浏览器对页面渲染有不同的标准,这种渲染方式叫做混杂模式(怪异模式)
在W3C标准出来之后,浏览器对页面的渲染有了统一的标准,这种渲染方式叫做标准模式
<!DOCTYPE>主要作用是告诉浏览器的解析器使用哪种HTML规范或者XHTML规范来解析页面。
<!DOCTYPE>不存在或者形式不正确会导致HTML或XHTML文档以混杂模式呈现,就是把如何渲染html页面的权利交给了浏览器(不同的浏览器对页面渲染有不同的标准)
盒模型:
在怪异模式下,盒模型为 IE 模型。盒子所占区域宽度=width(宽)+margin(左 右),高度等同
在标准模式下,盒模型为 W3C 模型。盒子所占区域宽=width(宽)+padding(左 右)+border(左右)+margin(左右),高度等同
行内元素的垂直对齐方式:
标准模式下 vertical-align 属性默认取值是 baseline;
怪异模式下 vertical-align 属性默认取值是 bottom。
字体样式:
标准模式下,表格中的字体样式会被继承;
怪异模式下,表格中的字体 样式不会被继承。
元素溢出的处理:
标准模式下,overflow 取值默认为 visible;
怪异模式下,当内容 超出容器高度时,会把容器拉伸。
!important:
标准模式下,IE7+认识!important 声明;
怪异模式下,IE6/7/8 都不认识!important 声明。
行内元素的宽高:
标准模式下,给行内元素设置 wdith 和 height 都不会生效;
怪异模式下会生效。
水平居中:
使用 margin:0 auto 在标准模式下可以使元素水平居中,
但在怪异模式下 却会失效。
怪异模式下,颜色值必须用十六进制标记法
margin
1、是用来隔开元素与元素的间距;
2、margin是可以设置负数,正数会产生距离,负数会重叠
3、margin上下折叠
4、margin对于内联元素上下不生效,对块和内联块都生效
5、给元素里的第一个子元素设置上边距的时候,会错误的显示在外层元素的身上(用padding代替)
padding
1、是用来隔开元素与内容的间隔
2、当元素不设置宽高时,设置padding是不会撑大盒子的
3、box-sizing:boder-box怪异盒解决撑大盒子
4、padding对内联元素左右显示正确,上下显示不准确,对块级和内联块没有任何问题
场景:
margin:
1、需要在border外侧添加空白时,空白处不需要背景色时;
2、需要使用负值对页面布局时(margin值可以取负值,padding不行)
3、上下相连得两个盒子之间的空白需要相互抵消时,如15px+20px得margin,将得到20px的空白。(margin折叠)
4、margin:auto会使块元素水平居中
padding:
1、需要在border内侧添加空白时,
2、空白处需要背景(色)时。
3、上下相连的两个盒子之间的空白,希望等于两者之和时。如15px+10px将得到25px的空白。
父元素上的操作
1、父元素 : 形成弹性盒 display:flex;
2、子元素在主轴上的排列位置:justify-content:
flex-start 主轴起点
flex-end 主轴终点
center 主轴中心
space-between 两端对齐
space-around 中间留白是两端的2倍
space-evenly 留白平白
3、子元素在交叉轴的位置 align-items
sretch 拉伸 需要去掉子元素高度才能看到拉伸
flex-start 交叉轴起点
flex-end 交叉轴终点
center 交叉轴中心 ,居中
4、主轴方向 flex-direction
row 从左到右
column 从上到下
row-reverse 从右到左
column-reverse 从下往上
5、换行弹性盒flex-wrap:
nowrap(默认不换行)
wrap(换行)
wrap-reverse 反向换行
6、多行之间的对齐方式(多行) align-content
sretch 拉伸
flex-start 盒子的起点
flex-end 盒子的终点
center 盒子中心
space-between 盒子两端
space-around 中间留白是两端的2倍
space-evenly 盒子上下留白平均
子元素上的操作
1、单独调整某个子元素在交叉轴的对齐方式 align-self
sretch 拉伸 需要去掉子元素高度才能看到拉伸
flex-start 交叉轴起点
flex-end 交叉轴终点
center 交叉轴中
2、子项排序 order:数字;值越大越在后面,可以设置负数
3、子项放大比例 flex-grow:数字 默认值0(不放大) 分配整个子
4、 元素的剩余空间
5、子项压缩 flex-shrink:数字 0(不压缩) 1(压缩)
实现导航的滚动效果
a. 子项的宽度超出了父容器的宽度
b. 设置子项不压缩 flex-shrink:0;
c. 父元素设置溢出显示滚动条 overflow-x:auto;
6、子项宽度 flex-basis: 数值px类似于width
7、复合写法 flex:子项放大比例(0) 子项压缩(1) 子项宽度(auto);
flex:1; 类似于flex-grow:1;各占一份
来实现禁用效果,使其不可用,不可点击
1、纯css实现标签的禁用,给盒子添加该属性pointer-events
style=“pointer-events: none”
disabled = false
2、借助JavaScript的方法(借助Jquery实现html中a标签的禁用)
<html> <head> <title>03 ——借助Jquery实现html中a标签的禁用</title> <meta content="text/html; charset=GB2312" http-equiv="Content-Type"> <script type="text/javascript" src="./jquery-1.6.2.js"></script> <script type="text/javascript"> $(function() { $('.disableCss').removeAttr('href');//去掉a标签中的href属性 $('.disableCss').removeAttr('onclick');//去掉a标签中的onclick事件 $(".disableCss").css("font","12px/1.5 \\5B8B\\4F53, Georgia, Times New Roman, serif, arial"); $(".disableCss").css("text-decoration","none"); $(".disableCss").css("color","#afafaf"); $(".disableCss").css("outline","0 none"); $(".disableCss").css("cursor","default"); }); </script> </head> <body> <a class="disableCss" href="http://www.baidu.com/">百度</a> <a class="disableCss" href="#" οnclick="javascript:alert('你好!!!');">点击</a> </body> </html>
1、flex 是 flexible Box 的缩写,意为“弹性布局”,用来为盒状模型提供最大的灵活性, 任何一个容器都可以指定为 flex 布局。当为父盒子设置为 flex 布局之后,子元素的float、clear、vertical-align 属性将失效。 •
2、采用 flex 布局的元素,称为 flex 容器(flex container),简称“容器”。他的所有子元 素自动成为容器成员,称为 flex 项目(flex item),简称“项目”。
3、Flex 容器默认存在两根轴:水平的主轴(main axis)和垂直的交叉轴(cross axis)。项目默认沿主轴排列,当然项目的排列方向也可以通过改变属性来控制。
4、总结:flex 布局就是通过给父盒子添加 flex 属性,来控制子盒子的位置和排列方式。
1、区别
px:就是量取的物理像素
em:根据父元素的字体大小改变: 1em=父元素font-size
rem:根据根元素的字体大小改变: 1rem=根元素font-size
将元素的大小设置为rem,那么其大小就会随着根元素的字体的大小改变而改变,从而达到在不同的设备都能同比例显示,
2、Px
像素 px 是相对于显示器屏幕分辨率而言的,就相当于长度单位;用 px 设置字体大小时,比较稳定和精确
3、em
根据父元素的字体大小改变,如果父元素字体没设大小,就根据浏览器的默认字体尺寸改变
4、rem
1、结构层
由HTML或者XHTML之列的标记语言创建,搭建页面结构
2、样式层
有CSS(层叠样式表)定义,是页面变得更好看一些
3、行为层
是网站具有交互性,允许页面响应用户操作或给予一组条件进行更改,最常用的语言是JavaScript,
实现页面在不同设备下的正常预览,(根据设备显示的特征(视口宽度、屏幕比列、设备方向)来设定CSS样式)
媒体查询 :通过查询当前属于哪种设备,让网页能够在不同的设备下正常的预览
媒体:指各种设备(移动设备,PC设备)
查询:要检测属于哪种设备
媒体类型:将不同的设备划分为不同的类型
all 所有设备
print 打印室设备
screen 电脑屏幕、平板电脑、智能手机
媒体特性:用来描述设备的宽度,高度...
width 网页显示区域完全等于设置的宽度
height 网页显示区域完全等于设置的高度
max-width / max-height 网页显示区域小于等于设置的宽度
min-width / min-width 网页显示区域大于等于设置的宽度
orientation: portrait (竖屏模式) | landscape (横屏模式)
语法关键字:将媒体类型和媒体特性链接到一块,进行设备检测
and 可以将多个媒体特性链接到一块,相当于且
not 排除某个媒体特性 相当于非,可以省略
only 指定某个特定的媒体类型, 可以省略
书写说明 :
and 两侧必须有空格
媒体特性属性值后面不要加分号
多个媒体特性之间用 and 连接
语法:
<style> 1、// @media 设备类型 and (媒体特性){} @media screen and (max-width:420px){ body{ background-color:red //当设备宽在420px以内时,背景色为红色 } } 2、//设备多个条件连写 @media screen and (max-width:420px) and (max-height:300px){} <style/> 3、//媒体查询使用步骤 a: 在网页头部添加这一行代码 <meta name="viewport" content="width=device-width,initial-scale=1.0,maximum-scale=1.0,user-scalable=no" > 这几个参数的意思: width=device-width 屏幕和设备同宽 initial-scale=1.0 初始的缩放比例(默认为1.0) maximum-scale=1.0 允许用户缩放的最大比例(默认为1.0) minimum-scale=1.0 允许用户缩放的最小比例(默认为1.0) user-scalable=no 用户是否可以手动缩放(默认为no) viewport 视口: 1. 布局视口,默认情况下,布局视口的宽是 980px,设置 css 样式的样式是作用在布局视口 2. 可视视口设备的宽度 device-width 3. 完美/理想视口 width=device-width 布局视口和设备宽度一样 b:兼容IE 因为IE8既不支持HTML5也不支持CSS3Media,所以需要两个JS文件来实现兼容 [if lt IE 9] <script src="https://oss.maxcdn.com/libs/html5shiv/3.7.0/html5shiv.js"></script> <script src="https://oss.maxcdn.com/libs/respond.js/1.3.0/respond.min.js"></script> [endif]
rem:
有局限性,IE8 及以下版本不支持
对 pc 页面来讲使用次数不多
数据量大:所有的图片、盒子都需要给一个准确的值,才能保证不同机型的适配;
@media:
应用广泛 适用于 pc端 手机页面,通常做自适应布局时 我们比较常用。
1、在ie浏览器中,a标签套图片会自带边框 ie10及以下
解决:去掉边框 img{border:none}
2、图片自带底部3px的留白
解决:
vertical-align: bottom/middle/top 给图片添加
display:block; 给图片添加
font-size:0; 给父元素添加
3、表单元素对齐不一致
解决:
设置怪异盒模型
设置浮动
4、透明度 opacity 在ie浏览器中不支持 0-1
解决:
opacity的值照常设置,适应正常的浏览器
单独设置ie中透明属性:filter:alpha(opacity=value);取值范围 value: 1-100(整数)1 完全透明 100不透明
不论水平还是垂直居中:
行内元素:text-align:center / line-height
块元素:margin:auto / 定位position+盒模型margin(要知道子元素的宽高) / 定位position+变形位移transform : translate(-50%,-50%); / 弹性盒flex、主轴和交叉轴的中心:display:flex;justify-content: center; align-items:center; 定位:父元素position:relative;子元素: position:absolute;top:50%;left:50%;
1、绝对定位法:将左右两边使用绝对定位,绝对定位使其脱离文档流,后面的 center 会自然流动到他们上面,然后使用 margin 属性,留出左右元素的宽度,就可以使 中间元素自适应屏幕宽度。
2、自身浮动法:对左右分别使用 float:left 和 float:right,浮动使左右两个元素脱离文 档流,中间元素正常在文档流中,使用 margin 指定左右外边距对其进行一个定 位。
3、margin 负值法:左右两栏均左浮动,左右两栏采用负的 margin 值。中间栏被宽度 为 100%的浮动元素包起来。
DOCTYPE是document type (文档类型) 的缩写。<!DOCTYPE >声明位于文档的最前面,处于标签之前,它不是html标签。主要作用是告诉浏览器的解析器使用哪种HTML规范或者XHTML规范来解析页面。
在W3C标准出来之前,不同的浏览器对页面渲染有不同的标准,这种渲染方式叫做混杂模式(怪异模式)
在W3C标准出来之后,浏览器对页面的渲染有了统一的标准,这种渲染方式叫做标准模式
<!DOCTYPE>主要作用是告诉浏览器的解析器使用哪种HTML规范或者XHTML规范来解析页面。
<!DOCTYPE>不存在或者形式不正确会导致HTML或XHTML文档以混杂模式呈现,就是把如何渲染html页面的权利交给了浏览器(不同的浏览器对页面渲染有不同的标准)
1、浏览器内核是什么东西。英文叫做:Rendering Engine(渲染网页内容的),中文翻译很多,排版引擎、解释引擎、渲染引擎,现在流行称为浏览器内核.
2、浏览器内核就是负责读取网页内容,整理讯息,计算网页的显示方式并显示页面.
3、Rendering Engine浏览器内核,顾名思义,就是用来渲染网页内容的,将开发者写的代码转换为用户可以看见的完美页面。由于牵扯到排版问题,所以肯定会排版错位等问题。为什么会排版错位呢?有的是由于网站本身编写不规范,有的是由于浏览器本身的渲染不标准。现在有几个主流的排版引擎,因为这些排版引擎都有其代表的浏览器,所以常常会把排版引擎的名称和浏览器的名称混用,比如常的说IE内核、Chrome内核。 但一个完整的浏览器不只包含排版引擎,还有自己的界面框架和其它的功能相辅相成的
4、主流的排版引擎和浏览器。
浏览器 | 内核 | 备注 |
火狐firefox | Gecko | 可惜这几年已经没落了,打开速度慢、升级频繁、猪一样的队友flash、神一样的对手chrome。 |
IE | Trident | IE、猎豹安全、360极速浏览器、百度浏览器 |
苹果Safari / 谷歌旧版本 | webkit | 从Safari推出之时起,它的渲染引擎就是Webkit,一提到 webkit,首先想到的便是 chrome,可以说,chrome 将 Webkit内核 深入人心,殊不知,Webkit 的鼻祖其实是 Safari。 |
谷歌chrome | Chromium/Blink | 在 Chromium 项目中研发 Blink 渲染引擎(即浏览器核心),内置于 Chrome 浏览器之中。Blink 其实是 WebKit 的分支。大部分国产浏览器最新版都采用Blink内核。二次开发 |
欧朋Opera | blink | 现在跟随chrome用blink内核 |
1. 设置元素宽高为0,必须是块或者内联块
2. 设置四个方向的边框为透明 border: 16px solid transparent;
3. 留下单方向 border-right: 16px solid white;
4.还需要给该元素添加绝对定位 这样脱离文档流 就不会影响后面的元素
div{ height:0; width:0; border: 16px solid transparent; border-top: 16px solid pink; //向下的三角形 position:absoult }
1rem=1个根元素font-size
1em=1个父元素font-size
1vw=视口宽度的1%
1、归属的差别:link 属于 HTML 提供的引用方式,@import 是 css 提供的引用方 式,link 还可以引入其他文件类型,@import 只能引入 css 文件
<link rel="icon" type="images/x-icon" href="图标路径">
@import url("图标路径"); 不可以引入
2、加载顺序的区别:link 和 HTML 是同时加载的,@import 是当所有 html 文件加载 后再去加载 css 文件,所以有时候浏览@import 加载 CSS 的页面时开始会没有样 式
3、兼容性 @import 只有 ie5 以上才支持
数值类型number:包含数字和null
字符串类型string:被单双引号包裹的
布尔类型boolean:true/false
undefined:声明却未初始化
null:声明变量,且赋值为null空
symbol:表示独一无二的值:es6新增
typeof:只能判断基本数据类型,引用类型返回的是object,所以引用类型使用
typeof 一般只能返回如下几个结果: number, boolean, string, function, object, undefined
instanceof判断具体的数据类型,比如数组、对象、函数
typeof返回的是个字符串,只能判断基本数据类型的数据类型,而对于引用类型来说,只能返回对象或者函数,
而insstanceof主要是判断引用数据类型,返回一个布尔值,但是需要制定一个特定的类型
是一种访问方式,与传统的访为方式不同,他在用户和服务器之间增加了缓存区,在缓存区中根据用户的请求定向到最近的缓存服务器上去获取内容,通过这种就近访问就减少了服务器源站点的压力,从而解决网络拥堵状况,提高用户的访为速度
Ajax是允许浏览器与服务器通信而无须刷新当前页面的技术(异步请求的技术)
用来请求数据,1.实例化一个XMLHttpRequest对象
2.设置请求参数xhr.open(请求类型(post还是get),地址(发送给谁),是否异步)
3.发送请求xhr.send( )
4.等待服务器的响应xhr.onreadystatechange,(在服务器发送请求时,readystate的值发生改变触发该事件),当小黄人的状态吗为4时,http协议为200时,通过responseText获得后端传来的数据
let xhr=new XMLHttpRequest() //1.实例化一个XMLHttpRequest对象 xhr.open("get","ajax.txt",true) //2.设置请求参数xhr.open(请求类型(post还是get),地址(发送给谁),是否异步) xhr.send() //3.发送请求 xhr.onreadystatechange=function(){ //4.等待服务器的响应 if(xhr.status==200&&xhr.readyState==4){ //5.当小黄人的状态吗为4时,http协议为200时 console.log(xhr.responsText) //6.获得后端传来的数据 } }
readystate是xhr对象在不同时刻的状态吗
0 xhr对象刚创建出来
1 open规划请求后
2 请求已经接受
3 请求处理中
4 请求已完成,且准备响应
5.如果是get传参:在请求地址后用?拼接key=value,每对键值对用&连接
如果是post传参,在send方法里面写参数,但是要加请求头xhr.setRequestHeader("Content-type","application/x-www-form-urlencoded");
第一种,利用它自己不等于自己的方法,如果返回值为ture,那么该数据就不是NaN,反之则为NaN
//第一种方法 NaN=NaN //false //第二种方法 Number.isNaN(NaN) //true //第三种方法 Object.is(n, NaN) //true
第二种,利用其内置的方法isNaN:当 isNaN(n) && n=="number" 两者都为true的时候,那么该数据就是NaN
第三种,ES6的Object.is方法,结果同第二种:Object.is()方法判断两个值是否是相同的值
function myIsNaN3(n) {
return Object.is(n, NaN)
}
null代表变量声明且被赋值为null(空),undefind是变量声明确未被初始化
相同点:两者在if判断中,都返回为false
是指元素上的事件被触发了之后,事件传递的两种方向
冒泡,是指先触发子元素,在依次触发父元素,捕获相反
what:闭包是指函数的嵌套,被嵌套的函数就称为闭包函数
why:可以再函数体外使用函数体内的局部变量
how:在函数体内ruturn 一个子函数,在子函数体内使用父函数的局部变量,在父函数体外,将父函数调用赋值给一个全局变量,那么子函数和其体内的父函数的局部变量就变成了长生命周期
优点:避免全局变量的污染,变量长期驻在内存中
特点:不会被垃圾回收机制回收
缺点:如果滥用,则会造成内存泄露
解决:闭包在不使用时,要及时释放,将引用内层函数对象的变量赋值为null
何时使用:要重复使用一个变量,又要保证变量不会被污染
注:
全局变量:优:可重复使用,缺:易被污染
局部变量:优:仅函数内部使用,不会被污染 ,缺:不可重复使用
1、异步:就是你需要等这个异步完成了,才能进行下一步,但async执行的函数和后面的函数是同时执行的,不会等待此函数成功执行后再执行下面的函数
2、JS的异步操作解决方案历程:回调函数---promise对象--- Generator函数---async/await终极解决方案
3、ECMAScript是JavaScript的一个标准,async/await 是一种编写异步代码的新方法,让异步代码看起来、表现起来更像同步代码。
概念:
ES7 的async/await 就是 Generator 的语法糖(简化),是异步编程终级解决方案,使得异步操作变得更加方便
async 作为一个关键字放到函数的前面,用于表示函数是一个异步函数(但会同步执行),该函数的执行不会阻塞后面代码的执行,
在函数内部使用 await 来表示异步,在后面放一个返回promise对象的表达式,
用await声明的Promise异步返回,必须“等待”到有返回值的时候,代码才继续执行下去(有阻塞作用)
作用:
使回调地狱的处理看起来比promise更美观,而且使用async来传参的时候比较方便。
是为了解决大量复杂不易读的Promise异步的问题
使用步骤:
定义一个需要进行异步等待的方法,并在方法前加"async"关键字
在这个内部有异步请求的方法中用await等待相应的请求完成。
在这个异步请求的方法中返回一个Promise对象,并封装resolve和reject方法
// //async函数返回一个promise对象,可以使用then方法添加回调函数 //当函数执行的时候,一旦遇到await就会先返回await后面的promise对象,等到触发的异步操作完成,在接着执行函数体内下面的语句 <script> async function f(){ //一个函数如果加上 async ,那么该函数就会返回一个 Promise //await的右侧表达式是其它的值,那么该值就是await的返回值 return 888 //如果在 async 函数中直接 return 一个直接量,async 会把这个直接量通过 PromIse.resolve()封装成Promise对象返回。 //2.await的右侧表达式是一个promise对象,则await返回promise成功的值 return await new Promise((resolve,reject)=>{ resolve("OK") reject("Error") }) //3.接受异常 try{ await promise对象 }catch(error){ console.log(error) } } console.log(f()) //await关键字在执行下一行代码之前等待右侧表达式(可能是一个Promise)返回。 //async/await 的优势在于处理 then 的调用链,能够更清晰准确的写出代码,并且也能优雅地解决回调地狱问题。当然也存在一些缺点,因为 await 将异步代码改造成了同步代码,如果多个异步代码没有依赖性却使用了 await 会导致性能上的降低。 <script/>
1.each()方法:遍历数组和对象
let obj = { "k1":"v1" "k2":"v2" "k3":"v3" "k4":"v4" "k5":"v5" "k6":"v6" } $.each(obj,function(key,val)=>{ //其中key是obj的key,val指相对应的值; /其中key是指数组的下标,val指相对应的数组 console.log(key,val) //打印出key 和相对应的value })
2.for in object:对象中的key就是下标
for(let key in obj){ console.log(key,obj[key]) //打印出key 和相对应的value }
3.使用Object.keys( )
Object.keys(obj).map(key=>{ console.log(key) //返回一个数组 })
也是事件代理,利用事件冒泡,将子元素要完成的功能委托给父元素完成
优势:可以批量的绑定元素,只绑定在父元素身上,提高程序效率
可以给未来添加的元素提前绑定事件
真实的事件源:兼容写法:l et target=e.scrElenment || e.target
target.tagName=="Li" //该属性输出的是,真实操作员的大写标签名
特性 | cookie | localStorage | sessionStroage |
数据的生命周期 | 一般由服务器生成,可设置失效时间,如果在浏览器端生成,默认关闭浏览器后失效 | 除非被清除,否则一直存在 | 仅在当前会话有效,关闭页面或浏览器后被清除 |
存放数据大小 | 4k左右 | 4-5MB | |
与服务器端通信 | 每次都会携带在HTTP请求头,使用cookie过多,会带来性能问题 | 仅在客户端(即浏览器)中保存,不参与服务器的通信 | |
易用性 | 源生的cookie接口不友好,需要程序员自己封装 | 源生接口可以接受,亦可再次封装来对object和Array有更好的支持 |
localStorage和sessionStorage:两者具有相同的方法
1、增改(key值存在为改,不存在为增)
1)对象.setItem(key,value)
2)对象.key
3)下标法:对象[key]
eg://无则增,有则改 localStorage.setItem("name","nini"); localStorage.age = 20; localStorage["id"] = 1; window.onbeforeunload = function(){ //还能存储一个json字符串 localStorage.data = '{"name":"hihi","age":16}'; }
2、查 / 取
1)对象.getItem(key);
2)对象.属性
3)下标法:对象[key]
eg: console.log(localStorage.getItem("name")); console.log(localStorage.age); console.log(localStorage["id"]); let json = JSON.parse(localStorage.data); //将json字符串转成json对象 console.log(json);
3、遍历本次存储的key
eg: //key(i):返回下标i对应的 key值 //localStorage.length:返回key或value队列的长度 for(let i = 0; i < localStorage.length; i++){ console.log(localStorage.getItem(localStorage.key(i))); }
4、删除:针对于sessionStorage
localStorage.removeItem("name");//根据key值 删除Storage中对应的键值对 localStorage.clear();//全部清除
浏览器缓存就是把一个已经请求过的Web资源,拷贝一份副本存在浏览器中,缓存会根据用户的请求保存输出内容的副本,当下一个请求来到的时候,如果是相同的URL,缓存会根据缓存机制决定直接使用副本响应访为请求,还是向源服务器再次发送请求!比较常见的就是浏览器缓存后资源后不会在更新,除非网站明确标识资源已更新
所谓 web 资源即放在 Internet 网上供外界访问的文件或程序,又根据它们呈现的效果及原理不同,将它们划分为静态资源和动态资源。
const 和 let
有了块级作用域,变量声明不会提升
let
模板字符串
通过一种更加简便的方法去拼接字符串
箭头函数
与function声明的区别:
函数的参数值默认值
ES6允许给函数参数赋初始值
可以与解构赋值一起使用
在书写形参时,直接给形参赋值。如果调用函数时,没有给对应的参数赋值,那么则会自动使用默认值。
对象和数组解构
对数组或者对象快速取值的一个小技巧(ES6许按照一定模式从数组和对象中提取值,对变量进行赋值)
结构的过程就是一一对应赋值,最后,只要拿取到被赋值的变量就能得到该值
如果是解构对象,那么我们解构赋值之后,要拿取该值时,就不需要对象打点调用,而是可以直接拿取
解构数组 let arr=[11,22,33,44,5] let [a,b,c,d,e] = arr console.log(b) //解构完的数组,不用数组[下标],而是可以直接拿取 解构对象 let obj={name:""张艳清,age:23} let {name}=obj console.log(name) //解构完用数据就不需要打点调用,而是直接使用
由于undefined和null无法转为对象,所以对他们进行解构赋值,都会报错
for...of for...in
ES6中的类
用class定义类,里面有构造方法,类之间通过extends关键字实现,子类必须在constructor方法中调用super方法
扩展运算符
...是他的语法
扩展运算符是把一个对象或数组快速展开的过程 :就是将变量a的内容放进去,显得页面简洁
简化对象写法
当变量名和值相同时,可以省掉值
Symbol
ES6引入了一种新的原始数据类型Symbol,表示独一无二的值。它是JavaScript语言的第7种数据类型,是一个类似字符串的数据类型
set
set集合也是一个装数据容器:
1、没有下标,自动去重
2、set数据结构类似于数组,其成员的值都是唯一的
let arr=[1,2,3,5,4,4,3,3] let set=new Set(arr) //将arr数组放到set集合里面去重, Array.from(set) //将去完重的set容器转换为数组 arr=Array.from(set) //将set集合重新转换/赋值给原数组 复合写法:let arr = Array.from(new Set(arr))
promise对象:存放异步代码,获取异步操作的成功或失败结果
class类:用class关键字来定义类,
for…in是遍历数组 和 对象的key值
let arr=[1,2,3,4] for(let i in arr){ console.log(i) // 输出下标 } let obj={name:"张艳清",age:23} for(let key in obj){ console.log(key) //输出key值 } //如果for..in 想遍历value值,在遍历的时候直接将对象或数组的输出改成console.log(arr[i] 或者 obj[key]) //输出value值
for...of 是遍历数组的value
let arr=[1,2,3,4] for(let value of arr){ console.log(value) //输出的是value值 }
区别:
1.for..in 可以遍历数组和对象,遍历输出结果为下标或key值
for...of 只能遍历数组,遍历结果为数组的value值
2.对于数组的遍历,for … in会返回数组中所有可枚举的属性(包括原型链上可枚举的属性),for … of只返回数组的下标对应的属性值
3.for … of循环的原理其实也是利用了遍历对象内部的iterator接口,将for … of循环分解成最原始的for循环,内部实现的机制可以这么理解
•var声明的变量会挂载在window上,而let和const声明的变量不会;
•var声明变量存在变量提升,let和const不存在变量提升;
•let和const声明变量都没有函数作用域的概念,而是遵守块级作用域的概念;
•同一作用域下let和const不能声明同名变量,而var可以;
•let有暂存死区(在声明之前就使用变量,就会报错,这就是暂时性死区)
•let和const关键字:let和const声明变量都没有函数作用域的概念,而是遵守块级作用域的概念,并且没有变量提升的操作,不能重复声明。const是声明常量版的let
从高到底适配,从低到高适配
高低版本的浏览器,向上向下兼容
1.push
功能:尾插,
参数:arr.push(参数1,[参数2...]);
返回值:新数组的长度
是否改变原数组:会改变
2.pop
功能:尾删,
参数:pop(无)
返回值:被删除的元素
是否改变原数组:会改变
3.unshift
功能:头插,
参数:unshift(参数1,[参数2...]);
返回值:新数组的长度
是否改变原数组:会改变
4.shift
功能:头删,
参数:shift(无),
返回值:被删除的元素
是否改变原数组:会改变
5.splice
功能:删除指定区间元素,并用新的数据代替,删除或替换
参数:splice(起始位置,偏移量,[新数据1,新数据2...])
返回值:删除的区间,
是否改变原数组:会改变原数组
6.join
功能:将数组按照间隔符转换为字符串,
参数:join([间隔符字符串]),默认间隔符为逗号,
返回值:返回字符串
是否改变原数组:不改变
7.reverse
功能:逆序,
参数:reverse(无)
返回值:无
是否改变原数组:会改变
8.slice
功能:数组区间的截取,
参数:slice(起止位置,结束位置);左闭右开[3,8);
返回值:被删除的区间;
注意事项:不会改变原数组;
9.concat
功能:将若干个数组拼接到一起,
参数:concat(数组1,[数组2...]);
返回值:被拼接的新数组,
是否改变原数组:不改变
10.indexOf
功能:查找数组元素,找到返回下标,找不到返回-1,
参数:indexOf(目标元素)
返回值:找到返回下标,找不到返回-1
11.forEach
功能:对数组的所有元素执行某个相同的操作
参数:forEach(功能模块),
function(元素的数值,[元素的索引](即下标),[元素所在的数组]){
函数体;
}
返回值:无
是否改变原数组:不改变
let arr=[a,b,c] arr.forEac(function(item){ //或者function(item,index,arr) console.log(item) //a,b,c }) //简写如下 arr.forEach((item)=>{ console.log(item) })
12.map(和forEach几乎一样)
有返回值
注意事项:map的回调函数有return才会在该元素中返回一个数值,如果没有return,那么只有空间没有数值
是否改变原数组:不改变
13.filter(和map差不多)
功能:过滤
filter有return才有空间和数值,没有return就没有空间
filter只能返回当前元素的数值
是否改变原数组:不改变
arr.filter(funcion(v,i){ return v }) //i也可以省略掉 //简写如下 arr.filter((v,i)=>{ return v })
14.Sort
排序
数组长度:改变
1、ASCLL码表
65 A
97 a
32 空格
13 回车
48 字符0
2、length字符串的长度
3、注意:字符和asc码值完全等价
1.charAt
功能:返回索引(下标)对应的字符
参数:charAt(索引)
返回值:索引对应的字符
2.charCodeAt
功能:返回索引对应的字符的ASC码值
参数:charAt(索引)
返回值:索引对应的字符的ASC码值
3.fromCharCode
功能:将asc码转换为字符,
参数:String.fromCharCode(asc1,[asc2...]);
返回值:返回asc码对应的字符,
注意:该方法直接通过String调用
4.indexOf
功能:查找字符串第一次出现的位置,如果没有则返回-1
参数:indexOf(字符串)
返回值:找到返回下标,反之返回-1
5.lastIndexOf
功能:查找字符最后一次出现的位置
参数:lastIndexOf(字符串)
返回值:找到返回下标,反之返回-1
6.replace
功能:字符串的替换
参数:replace(被替换的字符(/原/g,全局替换),替换字符串)
返回值:被替换的字符串
7.slice/substring
功能:截取字符串
参数:slice/substring(起始位置、结束位置)(左闭右开:包含开始,不包含结束)
返回值:被截取的字符串
substring的第二个参数不允许传负数
8.split
功能:将字符串切割为数组
参数:split(“切割字符串”)
返回值:返回一个数组
9.转为大写-->toUpperCase()
参数:oUpperCase(字符串)
10.转为小写-->toLowerCase()
参数:toLowerCase(字符串)
11. search
功能:返回匹配字串的首位下标
参数:search(正则对象)
返回值:找到返回下标,反之返回-1
12. Match
功能:根据正则格式返回匹配的字串,存入数组
参数:Match(正则对象)
返回值:数组
13. Includes
功能:是否找到参数字符串
参数:Includes(参数字符串)
返回值:布尔值
14. Startswith
功能:参数字符串是否在源字符串的头部
参数:Startswith(参数字符串)
返回值:布尔值
15. Endswith
功能:参数字符串是否在源字符串尾部
参数:Endswith(参数字符串)
返回值:布尔值
1.Math.floor(参数);向下取整 1.1---1,(-1.2)---(-2)
2.Math.ceil(参数);向上取整 1.1---2,(-1.2)---(-1)
3.Math.round(参数);四舍五入取整 1.2---1,1.9---2,(-1.9)---(-2)
4.Math.sqrt(number) 开平方根
5.Math.pow(m,n) 返回m的n次方
6.Math.min(1,-2,3,4) 返回N个数最小值
7.Math.max(1,-2,3,4)返回N个数最大值
8.Math.abs(number) 返回绝对值
9.Math.random():返回0~1之间的数,左闭右开
定义:获取当前时间:var d = new Date(yyyy-MM-dd[,hh:mm:ss] 放入时间参数日期格式字符串可以指定日期);年月日小时
1.d.getFullYear() 获取年
2.getMonth() 获取月 0~11
3.getDate() 获取日
4.getHours() 获取小时
5.getMinutes() 获取分
6.getSeconds() 获取秒
7.getDay 获取星期几 0~6 周日为0
1.setDate() 改变Date对象的日期
2.setHours() 改变小时数
3.setMinutes() 改变分钟数
4.setMonth() 改变月份,从0开始
5.setSeconds() 改变秒数
6.setFullYear() 改变年份
1.setInterval(回调函数,间隔);
clearInterval(定时器关闭的钥匙);
2.setTimeout(回调函数,延迟);
clearTimeout(定时器关闭的钥匙);
兼容
1.事件对象的兼容:
document.onclick = function(evt){
var e = evt || event;
console.log(e);
}
2.获取键盘asc码的兼容写法:
var key = e.keyCode || e.which || e.charCode;
注:e.ctrlKey事件触发时,判断ctrl键是否被按下:e.ctrlKey返回为布尔值
3.阻止冒泡事件的兼容写法:
e.stopPropagation?e.stopPropagation():e.cancelBubble = true;
4.阻止浏览器的默认行为:鼠标右键/超链接
e.preventDefault?e.preventDefault():e.returnValue = false;
方法二:return false
5.事件委托的兼容方法:
var target = e.srcElement || e.target;
获取当前鼠标位置:
clientX clientY 原点位置: 可视窗口的左上角为原点
offsetX /offsetY 原点位置: 最近的父元素左上角为原点 常用于拖拽
pageX / pageY 原点位置: 整个页面的左上角(包含滚出去的滚动距离)
鼠标事件:(可以绑定在任意元素节点上)
click:单击 dblclick:双击
mouseover:鼠标移入 mouseout:鼠标移出
mousedown:鼠标按下 mouseup:鼠标抬起
ouseenter:鼠标移入 mouseleave鼠标移出
mousemove:鼠标移动(会不停的触发) contextmenu鼠标右键点击
键盘事件:所有键盘事件的事件源都是大白板
onkeyup:键盘抬起的那一刻;onkeydown:只要按下按键就会触发,无论是否为功能键
onkeypress:生成一个字符的时候触发事件,功能键没用常用
HTML事件:
1、window事件
load:当页面加载完成以后会触发
unload:当页面解构的时候触发(刷新页面,关闭当前页面) IE浏览 器兼容
scroll:页面滚动
resize:窗口大小发生变化的时候触发
2、表单事件
blur:失去焦点
focus;获取焦点
select:当我们在输入框内选中文本的时候触发
change:当我们对输入框的文本进行修改并且失去焦点的时候
input:生成字符触发
取消事件绑定:节点.事件类型=null
单个字符:
1. ^:正则开始
2. $ : 正则结束
3. . : 元字符, 表示任意一个字符
4. \. : 表示转义字符 \.表示.
5. +: 表示其前面紧挨着的字符至少出现1次 等价{1,}
6. * :表示其前面出现的字符至少出现过0次 等价{0,}
7. ?: 表示其前面出现的字符至少出现过0次,至多1次 等价{0,1}
8. | : 表示或者
组合字符:
9. \d : 0-9之间的任意一个数字 \d只占一个位置
10. \D : 除了\d
11. \w : 数字,字母 ,下划线 0-9 a-z A-Z _
12. \W : 除了\w
13. \s : 空格或者空白等
14. \S : 除了\s
括号:
15. {m,n}表示括号前面紧挨着的字符至少出现m个,至多出现n个
16. {m}表示括号前面紧挨着的字符只能出现m个
17. {m,}表示括号前面紧挨着的字符至少出现m个
18. [ ] 表示括号内的任意一个字符 [wd3h]
19. [a-z]表示任意一个小写字母 [a-zA-Z0-9]
20. [^ ]表示非括号内的任意一个字符
21. ()一般与或连用 表示优先级
22. [\u4e00-\u9fa5] 任意一个中文字符
正则中的相关方法:
30.test():检验一个字符串是否符合某一个正则规范,如果符合返回true,否则返回false
31.exec 根据正则表达式查找,结果满足,会返回一个长度为1的数组(数组只有一个值)
32. g:全局 globel
正则中相关字符串的方法
33.search方法:返回与正则表达式查找内容匹配的第一个子字符串的位置 参数:search(正则对象);返回值:找到返回子串下标,找不到返回-1
34.i:忽略大小写
35.match方法:使用正则表达式模式对字符串执行查找,并将包含查找的结果作为数组返回参数:match(正则对象)
36.replace 方法:返回根据正则表达式进行文字替换后的字符串的复制
表单验证:
1、action:把数据提交到的服务器文件
2、method:数据发送的安全类型(默认为get)
get:不要求安全性的数据,效率高,安全性低,携带数据量小
post:要求安全性的数据,效率低,安全性高,携带数据量大
3、点击表单form里面的submit按钮 ,会直接跳转到action服务器地址中
4、onsubmit事件:当表单提交时触发该事件,当该事件返回值为true时,表单才能提交
a:通过数组API :join let arr=[1,2,4,5] let str=arr.join() //不加参数,默认使用逗号分隔 返回“1,2,4,5” b:toString() let arr=[1,2,4,5] let str=arr.toString() //返回“1,2,4,5” c:toLocaleString() let arr=[1,2,4,5] let str=arr.toLocaleString() //返回“1,2,4,5” c:两个数组相+:也返回一个字符串 let arr=[1,2,4,5] let arrb=[1,2,4,5] let str=arr+arrb //数组连接操作 返回“1,2,4,51,2,4,5”
push尾插、pop尾删、shift头删、unshift头插、reverse逆序、splice删除替代、sort排序
join将数组转为字串、slice截取删除、concat拼接数组、indexOf查找数组元素、forEach、map、filter都是遍历数组
forEach不会返回新的数组,而是在原数组的基础上改变数组,可以用于数组的修改,没有return
map不改变原数组,会将处理过的数据组成一个新的数组
filter不会改变原数组,但是也会将满足条件的元素组成印个新的数组,return出来
map和filter的区别主要在于,当过滤而不是改变的时候,map return的是一个盛放布尔值的数组
a:split() //该方法无法识别表情符号 let str="zxcv" let arr=str.split("")//通过使用空字符串作为split方法的分隔符 返回值['z','x','c','y'] b:扩展运算符 let str="zxcv" let arr=[...str] //返回值['z','x','c','y'] c:解构赋值 let str="zxcv" let [...arr]=str //返回值['z','x','c','y'] d:Array.from let str="zxcv" let arr=Array.from(str) //返回值['z','x','c','y']
a: json 是一种轻量级的数据交换格式 / 数据交换语言
b: JSON规则:类似于js对象
1.json对象里面是键值对
2.键必须用双引号包裹
3.键和值用冒号隔开,
4.并列的数据用逗号分开
5.值可以是字符串、数字、bool、null、对象、数组。
c: JSON.parse(data );----从json字符串转换成js对象
$.parseJSON(data);----从json字符串转换成js对象
JSON.stringify() ; -----把js对象转换成json字符串
d: 删除: delete obj['属性名']
添加:obj['属性名']=属性值
//json字符串 $str='{"name":"张艳清","age":23}'; //json对象 $str={"name":"张艳清","age":23}; // json数组 $arr=["name"=>"高少鑫","age"=>19]; //删除 delete str["name"] //添加 str["name"]=“赵利强”
a: 所谓的面向对象:就是一切操作都要通过对象;先创造对象,在进行组合
而程序中的所有对象都被分为两个部分:属性和方法;
面向对象想要操作对象,首先得有对象;如何创建对象,首先得定义类:
类是具有相同或相似性质对象的集合/模板,而对象是类的实例化
b: 面向对象的特点
封装:高内聚,低耦合,类内部可以任意修改,不会影响其他类
继承:通过继承可以将其他类中的属性和方法引到当前类中,在不修改本类的情况下,完成对本类的扩展
多态/重写:在继承时:如果子类的方法替换掉父类中的同名方法,这就称为多态
c: 面向对象就是把构成问题的事物分解成各个对象,建立对象不是为了完成一个步骤,而是为了描述某个事物在整个解决问题的过程中的行为
d: 优点:易维护,复用性高,扩展
缺点:性能低,因为在实例化对象的时需要很大的开销
1、构造方法必须通过new来调用
2、构造方法没有返回值
3、构造方法名字习惯首字母大写
4、构造函数是用来创建对象的,普通方法描 一类事物的公共行为
9.1 构造方法
在es5中,用函数来模拟类,该函数名被称为构造方法
在es6中,constructor被称为构造方法
9.2 原型对象:
1、es5中:共有的方法放在原型对象:Fun.prototype
2、es6中:书写的格式方法就直接是写在原型对象中的
a: 原型:每个函数(一般指构造函数),都有一个prototype属性,指向一个空对象(这个对象就是显式的原型对象)
该原型对象中存放着本类的实例对象所共有的方法和属性
每个构造函数有一个属性指向该类的原型对象 Fun.prototype = Fun类的原型对象 每个实例对象都有一个属性指向本类的原型对象 let f=new Fun(): Fun.prototype = f.__proto__ = Fun类的原型对象 每个原型对象都有一个属性指向该构造函数 Fun.prototype.constructor===Fun
b: 原型链:每一个实例化的对象都有一个__proto__属性,指向本类的原型对象(是隐式的原型对象);而类的原型对象因为是一个对象,所以也会有__proto__属性,也会指向另一个原型对象,层层递增,一直到顶层的object的原型对象;这就形成了一条原型链;
原型链的作用是:读取实例对象的某个属性时,先在该对象的本身寻找,如果找不到就去她的原型对象里面找,一直到最顶层,如果还是找不到,就返回null
c: 继承:继承就是子类可以使用父类里面的属性和方法;通过:我们在子类的构造函数中使用call和apply方法调用父类的构造函数并改变其this指向为子类构造函数的this(就是子类借助父类的)这样子类就继承了父类的私有属性和方法,在将父类的实例对象赋值给子类的原型对象,这样子类就继承了父类的原型属性和方法
function Animal(id, name) { this.name = name; this.id = id; } Animal.prototype.eat = function() { console.log("Animal eat"); } function Student(id, name, score) { //属性的继承 Animal.apply(this, [id, name]); // 方法名字.apply(改变后的this指向,[需要传入的参数]) this.score = score; } //原型对象上的方法和属性继承 Student.prototype = new Animal(); //无需在加参数 Student.prototype.study = function() { console.log("Student Study"); } let s = new Student(1, "武娜婷", 100); console.log(s); s.eat(); s.study();
apply和call:将一个方法和一个实例对象联系起来;是可以改变this的指向:比如:方法名.apply(改变后的this指向,[需要传入的参数])
function Animal(id, name) { this.name = name; this.id = id; } Animal.prototype.eat = function() { console.log("Animal eat"); } function Student(id, name, score) { //属性的继承 Animal.apply(this, [id, name]); this.score = score; } //原型对象上的方法和属性继承 Student.prototype = new Animal(); //无需在加参数 Student.prototype.study = function() { console.log("Student Study"); } let s = new Student(1, "武娜婷", 100); console.log(s); s.eat(); s.study();
1、apply 和call 都是改变this的指向
2、作用:和函数的关系进行解耦: 将类和方法分成两个模块,通过apply
或call将该方法与该类的实例化对象联系起来
3、格式:方法函数名.call(this指向(类实例化对象),方法函数的实际参数)
4、apply call bind的异同
1、全都是改变this指向 的 函数对象的方法
2、apply和call可以直接调用方法函数,bind相当于生成了一个新
的函数对象,不会调用
3、bind通常针对于匿名函数,apply和call常针对于有名函数
4、apply的参数需要用数组包裹起来,call不用
eg:function Snake(name){ this.name = name; } function Monkey(name){ this.name = name; } function eat(food1,food2){ console.log(`${this.name} eat: ${food1} ${food2}`); } let s = new Snake("小青"); let m = new Monkey("悟空"); eat.call(s,"老鼠","奥利奥"); eat.call(m,"桃子","香蕉"); eat.apply(s,["老鼠","奥利奥"]); eat.apply(m,["桃子","香蕉"]); eat.bind(s,"桃子","香蕉")();
promise是ES6新增,是解决异步操作的方法,比复杂嵌套的回调函数更简单,变成了平级嵌套
promise是一个构造函数( 类),可以通过new得到promise 实例对象
promisenew出来的实例化对象是一个异步操作,必须在实例化的时候传入一个函数,该函数体内就是我们要进行的异步代码
promise有两个函数,resolve( )异步代码成功时执行的函数,,reject( )失败的回调函数
而promise对象 可以帮我们将复杂嵌套的回调函数变成平级调用 (需要异步请求一个数据作为下一个异步操作的入参, promise 可以实现在多个请求发送完成后 再得到或者处理某个结果),避免了多级异步操作的回调嵌套的复杂性
promise对象内部有三种状态:初始状态padding、成功状态resolve、失败状态reject
promise对象有三种常用的方法:成功方法then()、失败方法catch()、all 把多个没有关系的 Promise 封装成一个 Promise 对象使用then 返回一个数组数据。
import service from "@/util/service.js" let getlink=(url)=>{ return new Promise((resolve,reject)=>{ service.request({ url, method:"get" }).then((ok)=>{ resolve(ok) }).catch((err)=>{ reject(err) }) }) } export default getlink
• 封装Ajax 异步请求的时候
• 函数嵌套层级多的时候使用 promise,优点在于,回调函数变成了链式写法,程序的流程可以看得很清楚,而且有一整套的配套方法,可以实现许多强大的功能
首先promise.all和promise.race 里面 都可以放一个 存储promise对象的数组
Promise.all()可以将多个实例组装个成一个新实例,成功的时候返回一个成功的数组;失败的时候则返回最先被reject失败状态的值
值得注意的是,返回的数组结果顺序不会改变,即使P2的返回要比P1的返回快,顺序依然是P1,P2
失败返回失败数据,一但失败就不会继续往下走
let p1 = Promise.resolve('aaa1') let p2 = Promise.resolve('aaa2') let p3 = Promise.resolve('aaa3') let p4 = Promise.resolve('aaa4') Promise.all([p1,p2,p3,p4]).then(res=>{ console.log(res) //返回数组 })
promise.race()
Promise.race是赛跑的意思,也就是说Promise.race([p1, p2, p3])里面的结果哪个获取的快,就返回哪个结果,不管结果本身是成功还是失败
一般用于和定时器绑定,比如将一个请求和三秒的定时器包装成Promise实例,加入到Promise队列中,请求三秒中还没有回应时,给用户一些提示或相应的操作。
使用场景:
Promise.all和Promise.race都是有使用场景的。
有些时候我们做一个操作可能得同时需要不同的接口返回的数据,这时我们就可以使用Promise.all;
有时我们比如说有好几个服务器的好几个接口都提供同样的服务,我们不知道哪个接口更快,就可以使用Promise.race,哪个接口的数据先回来我们就用哪个接口的数据。
只有promise对象可以打点调用then;而then里面是一个回调函数;我们在then的回调函数里面返回一个promise,就可以一直打点调then
网页上所用到的语言:html、css、JavaScript;html和css是确定页面的样子,而不同的浏览器在获取到页面代码文件后,而浏览器内核的作用就是将这些代码渲染出来呈现给用户,一个好的浏览器,一定是基于有一个稳定、高端、作用明显的浏览器内核的。
浏览器的作用:向服务器发送请求;将html、css、JavaScript代码渲染成页面(浏览器引擎);
ie 浏览器:Trident 火狐:Gecko 代码开源 苹果 & 谷歌旧版本: Webkit 谷歌 & 欧鹏: Blink
注:所谓的浏览器兼容性问题,是指因为不同的浏览器对同一段代码有不同的解析,造成页面显示效果不统一的情况
a:概念:
jQuery是js的库,宗 旨是写更少的代码,做更多的事
jQuery是一个js的文件,封装了原生js常用的功能代码,优化了DOM的操作、事件处理、动画设计和Ajax交互,链式调用
学习jQuery的本质就是:学习调用这些函数(方法)
b:优点:
轻量级,核心文件才几十kb,不会影响页面加载速度
跨浏览器兼容,基本兼容了现在主流的浏览器
链式编程,隐式迭代
对事件、样式、动画支持,大大简化了DOM操作
支持插件扩展开发,有着丰富的第三方插件;例如:树形菜单、日期控件、轮播图等
• 作用:
o 程序员角度:简化 Javascript 和 Ajax 编程,能够使程序员从设计和书写繁杂的
JS 应用中解脱出来,将关注点转向功能需求而非实现细节上,从而提高项目的
开发速度。
o 用户体验角度:改善了页面视觉效果,增强了与页面的交互性,体验更绚丽的
网 页物资方便地选择页面元素(模仿 CSS 选择器更精确、灵活) 动态更改页面
样式/页面内容(操作 DOM,动态添加、移除样式) 控制响应事件(动态添加响应
事件) 提供基本网页特效(提供已封装的网页特效方法) 快速实现通信(ajax)。
o jQuery 获取方式: jQuery 库文件不需要安装,只需使用 <script>标签引入
HTML 文件中,拿到 jQuery 的库文件后,就跟自己写的 JS 文件同样的引入方
式
1.引入本地的 jQuery
2.引入 cdn 在线提供的库文件(稳定可靠高速)
框架是一个半成品,已经对基础的代码进行了封装并提供相应的API,开发者在使用框架是直接调用封装好的api可以省去很多代码编写,从而提高工作效率和开发速度
就像是你买了一个高级烤面包机(框架,Framework),它有自己的一套烤面包流程,你要遵守它的规则和流程,才能考出面包来。而考面包的过程中使用的勺子啊,碗等就是工具(库,library)了。
在实际中,像angular、backbone、vue就属于框架,而jQuery、react、underscore就是库,在前者中我们完全可以自由的使用后者,同时也可以没有前者的基础之上使用后者,都是很自由,控制权始终在我们的手中,但是使用框架时候就必须按照它的规范来进行模块化的开发;
React和react-router-dom, react-redux结合起来才叫框架,本身只是充当一个前端渲染的库而已
Less 是一门 CSS 预处理语言(预处理器框架),最终都会编译成css,它扩展了 CSS 语言,增加了变量、Mixin、函数、js表达式(计算功能)、嵌套、颜色函数、代码的重用、继承 等特性,使 CSS 更易维护和扩展。Less 可以运行在 Node 或浏览器端
不同点:
1、sass要在ruby的环境才可以,less只是需要的是一个js文件和引入less文件,当然less也可以先使用node进行编译,之后再引入到页面中
2.变量的表达不同:less是使用$,sass使用的是@
3、sass是基于服务器端处理的,而less是客户端处理的
4.sass是可以进行输出的(4种编译排版模式nested,expanded,compact,compressed),而less不可以
5、sass是可以支持条件语句的
为什么使用?
1.结构清晰,便于扩展
2.可以方便的屏蔽浏览器私有语法差异
3.减少无意义的机械劳动,可以轻松实线多重继承
4.完全兼容css代码,可以方便的应用到老项目中
2.1.变量——SASS允许使用变量,所有变量以$开头。
2.2.计算功能——SASS允许在代码中使用算式
2.3. 嵌套———SASS允许选择器嵌套。
2.4 颜色函数
3.代码的重用
3.1.继承————SASS允许一个选择器,继承另一个选择器。
3.2。Mixin——Mixin有点像C语言的宏(macro),是可以重用的代码块。
3.34 插入文件
4.高级用法
1.1 条件语句
1.2 循环语句
1.3 自定义函数
跨域是因为浏览器的同源政策:所谓同源指的是两个页面具有相同的协议、主机和端口,三者有任一不相同即会产生跨域。
同源政策的目的,是为了保证用户信息的安全,防止恶意的网站窃取数据
同源策略的数据
o 存储在浏览器中的数据,如 localStroage、Cookie 和 IndexedDB 不能通过脚本
跨域访问
o 不能通过脚本操作不同域下的 DOM
o 不能通过 ajax 请求不同域的数据/请简述同源策略
this出现在构造方法中时,代表新new出来的对象
this出现在事件函数中时,代表触发该事件的函数
this出现在普通函数中时,代表调用这个函数的对象
this出现在箭头函数中时,箭头函数没有自己的this, 它的this是继承而来,箭头函数的this就是外层代码块的this一般指window
(1): 减少重复的http请求:比如可以将许多图片合成为一个单独的图片(精灵图),然后可以通过background-position属性来改变北京图片的位置,
(2):压缩文件:js,css,文件中一般存在大量的空格,换行,注释,将其压缩掉,则有利于网络传输
(3):优化CSS:a:压缩css b:使用预处理器框架sass/less,也方便后期维护
(4):优化图片:a:图像格式的选择(GIF:提供的颜色较少,可用在一些对颜色要求不高的地方)b:优化 CSS(压缩合并 css,如 margin-top,margin-left...) c:网址后加斜杠(如 www.campr.com/目录,会判断这个“目录是什么文件类型,或者是目录。)
(5):位置:
a:css、js内容比较庞大,则将其放到外面,改由外部引入,因为浏览器本身会对css、js文件进行缓存。
b:将CSS样式放在文件头部,将js脚本放在文件底部:所有放在 head 标签里的 CSS 和 JS 文件都会堵塞渲染,如果这些 CSS 和 JS 需要加载和解析很久的话,那么会造成白屏现象,故将js文件放在底部,等HTML解析完了再加载js文件,将CSS样式放在文件头部,因为若先加载HTML再加载CSS,则用户第一时间看到的页面是没有样式的,是‘丑陋’的,而这项设置对于用户端是慢速网络或网页内容比较庞大的情况比较有利,可以在网页逐步呈现的同时仍会保持格式信息,不影响网页美感。
(6):Ajax调用尽量使用GET:实际使用XMLHttpRequest时,如果使用POST方法实现,会发生2次HTTP请求,而使用GET方法只会发生1次HTTP请求。如果改用GET方法,HTTP请求减少50%!
(7):使用CDN内容分发网络,减少传输距离,缩短请求时间
(8):前端资源的动态加载:a:路由的懒加载 b:图片的懒加载 c:组件的动态加载
(9):尽可能减少DCOM元素:就是尽可能减少网页中各种<>元素数量,例如<table>的冗余很严重,而我们完全可以用<div>取代之。
a: jsonp是用来解决跨域的一种方式
b:原理:在前端动态生成一个script标签(就是点击按钮之后触发生成标签),利用scr属性可以跨域的功能,就可以跨域拿到后端我们需要的数据
c:为什么不是真正的Ajax:Ajax的核心是通过XMLHttpRequest获取非本页内容,jsonp只是一种跨域访问的技巧,和Ajax没有关系,它的核心是动态添加script标签调用服务器提供的js脚本;jsonp只支持get请求,Ajax支持get和post请求
// 1.借助数组APIindexOf() let arr=[1,2,3,4] let newarr=[] for(let i=0;i<arr.length;i++){ if(newarr.indexOf(arr[i])==-1){ newarr.push(arr[i]) } } console.log(newarr) // 2.借用includes 如果数组中存在查找的值,则返回true,否则返回false。 let arr=[1,2,3,4] let newarr=[] for(let i=0;i<arr.length;i++){ if(!newarr.includes){ newarr.push(arr[i]) } } console.log(newarr) //3.利用 ES6的set 方法:set数据结构类似于数组,其成员的值都是唯一的 let arr = Array.from(new Set(arr)); //利用Array.from将set结构转换成数组(类数组转为数组) 额外述说set:set集合也是一个装数据容器: 1、没有下标,自动去重 2、:set数据结构类似于数组,其成员的值都是唯一的 3、 let arr=[1,2,3,5,4,4,3,3] let set=new Set(arr) //将arr数组放到set集合里面去重, Array.from(set) //将去完重的set容器转换为数组 arr=Array.from(set) //将set集合重新转换/赋值给原数组 复合写法:let arr = Array.from(new Set(arr))
1.快速排序
2.冒泡排序
3.选择排序
4.sort排序
// 快速排序 var quickSort = function( arr) { if(arr.length < 1) { //如果数组就是一项,那么可以直接返回 return arr; } var centerIndex = Math. floor(arr.length / 2); //获取数组中间的索引 var centerValue = arr[centerIndex]; //获取数组中间项 var left = [], right = []; for( var i = 0; i < arr.lenght; i ++){ if(arr[i] < centerValue){ left. push(arr[i]); } else{ right. push(arr[i]); } } return quickSort(left). contanct([centerValue], quickSort(right)); //递归调用 } // 冒泡排序 for (var i = 0; i < arr.length - 1; i++) { for (var j = 0; j < arr.length - i - 1; j++) { if (arr[j] < arr[j + 1]) { //相邻元素两两对比 var t = arr[j]; //元素交换 arr[j] = arr[j + 1]; arr[j + 1] = t; } } } console.log(arr); // 插入排序 var insertSort = function( arr) { var len = arr.length; var preIndex, current; for( var i = 1; i < len; i ++){ preIndex = i - 1; current = arr[i]; while(preIndex >= 0 && arr[preIndex] > current){ arr[preIndex + 1] = arr[preIndex]; preIndex --; } arr[preIndex + 1] = current; } return arr; } ———————————————— 版权声明:本文为CSDN博主「Qin_ace」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。 原文链接:https://blog.csdn.net/sinat_40036449/article/details/80886337
JavaScript中的变量分为基本类型和引用类型。
1、基本类型
基本类型有Undefined、Null、Boolean、symbol、Number 和String。这些类型在内存中分别占有固定大小的空间,他们的值保存在栈空间,我们通过按值来访问的。
注:存取速度比堆快,仅次于直接位于CPU中的寄存器,数据可以共享
内存小
变量都是放在栈内存中,随着方法的执行结束,这个方法的内存栈也自然销毁
栈会自动分配内存空间,会自动释放,存放基本类型,简单的数据段,占据固定大小的空间。
2、引用类型
引用类型一般指object,数组,函数...值的大小不固定。栈内存中存放地址,地址指向堆内存中的具体数据,是按引用访问的。
3、为什么会有栈内存和堆内存之分?
通常与垃圾回收机制有关。为了使程序运行时占用的内存最小。
当一个方法执行时,每个方法都会建立自己的内存栈,在这个方法内定义的变量将会逐个放入这块栈内存里,随着方法的执行结束,这个方法的内存栈也将自然销毁了。因此,所有在方法中定义的变量都是放在栈内存中的;
当我们在程序中创建一个对象时,这个对象将被保存到运行时数据区中,以便反复利用(因为对象的创建成本通常较大),这个运行时数据区就是堆内存。堆内存中的对象不会随方法的结束而销毁,即使方法结束后,这个对象还可能被另一个引用变量所引用(方法的参数传递时很常见),则这个对象依然不会被销毁,只有当一个对象没有任何引用变量引用它时,系统的垃圾回收机制才会在核实的时候回收它。
1、拷贝:是指:用一个已有的对象初始化一个新的对象
2、深浅拷贝是针对于引用类型
3、引用数据类型在内存中存储是有俩个空间,堆空间存储数据,栈空间存堆空
间的地址(变量)
4、浅拷贝是:只拷贝引用地址,不开辟空间:两把钥匙,一个仓库
深拷贝是:开辟空间并且赋值,两把钥匙,两个仓库之间互不影响
5、深拷贝如何做:先开辟一个新空间,将原空间的元素遍历插入到新的空间中
let arr = [4, 8, 3, 5, 1] let arr1 = [] for (let i = 0; i < arr.length; i++) { arr1.push(arr[i]) } console.log(arr1); //手写深拷贝,json对象 let json = { "name": "张艳清", "age": 23 } let obj = {} for (let key in json) { //for…in是遍历数组 和 对象的key值 for...of 是遍历数组的value obj[key] = json[key] } console.log(obj);
1)强类型定义语言:
强制数据类型定义的语言。也就是说,一旦一个变量被指定了某个数据类型,如果不经过强制转换,那么它就永远是这个数据类型了。举个例子:如果你定义了一个整型变量a,那么程序根本不可能将a当作字符串类型处理。强类型定义语言是类型安全的语言。
2)弱类型定义语言:
数据类型可以被忽略的语言。它与强类型定义语言相反, 一个变量可以赋不同数据类型的值。
强类型定义语言在速度上可能略逊色于弱类型定义语言,但是强类型定义语言带来的严谨性能够有效的避免许多错误。
在js中一个变量我们却可以给他赋值各种类型:数值类型,字符串,布尔类型,对象类型等,为此我们可以推断出来,JavaScript为弱类型语言。
a: 在使用less之前请确保你的主机安装了Node.js,并且能够正常运行
b: 如果你已经安装了 Node ,那么只需要window + R输入cmd打开命令行工具。安装 less 用以下语句 :npm install -g less
c: 安装完less之后,用命令行切换到你需要转换的目标目录下,在当前目录命令行窗口输入lessc + less文件名称和后缀 > css文件名称和后缀(名称自定)像下面这样: lessc stale.less>style.css
a : Echarts使用最多的是:有着丰富的可视化类型,可以实现多种数据格式无需转换直接使用,可以实现千万数据的前端展现,一般使用在大数据可视化平台
ECharts,一个纯 Javascript 的图表库,可以流畅的运行在 PC 和移动设备上,兼容当前绝大部分浏览器(IE8/9/10/11,Chrome,Firefox,Safari等),底层依赖轻量级的 Canvas 类库 ZRender,提供直观,生动,可交互,可高度个性化定制的数据可视化图表。
丰富的图表类型
ECharts 提供了常规的折线图、柱状图、散点图、饼图、k线图,用于统计的盒形图,用于地理数据可视化的地图、热力图、线图,用于数据关系可视化的关系图,treemap,多维数据可视化的平行坐标,还有用于BI的漏斗图,仪表盘,并且支持图与图之间的混搭
动态数据
ECharts由数据驱动,数据的改变驱动图表展现的改变。因此动态数据的实现也变得异常简单,只需获取数据,填入数据,ECharts会找到两组数据之间的差异然后通过合适的动画去表现数据的变化。
移动端的优化
流量珍贵的移动端需要图表库的体积尽量小。ECharts和ZRender代码的重构,带来了核心部分体积的减小。ECharts和ZRender代码的重构带来了核心部分体积的缩小。ECharts提供按需打包的能力,因为ECharts的组件众多,并且会持续增加。
多维数据支持以及丰富的视觉编码手段
ECharts 3开始加强了对多维数据的支持。除了加入平行坐标等常见的多维数据可视化工具外,对于传统的散点图,传入的数据也可以是多个维度的。配合视觉映射组件visualMap 提供丰富的视觉编码,能够将不同维度的数据映射到颜色,大小,透明度,明暗度等不同的视觉通道。
for循环:在固定长度和长度不计算的情况下for循环效率更高
map循环:在不确定长度或者计算长度有损性能的时候用map比较方便,必须有返回值
//ES6: class Human{ constructor(name,id) { this.name = name; this.id = id; } eat(){ console.log("Human eat"); } } class Student extends Human{ constructor(name,id,score) { super(name,id); this.score = score; } study(){ console.log("Student study"); } } let s = new Student("nini",1,200); console.log(s.name,s.id,s.score); s.eat(); s.study(); //ES5继承: function Fu(name,age){ this.name=name this.age } Fu.prototype.eat=function(){ conlole.log('我是父类原型的方法') } function Zi(name,age,study){ Fu.apply(this,[name,age]) this.study } Zi.prototype=new Fu() let z=new Zi('张艳清',23,book) z.eat()
a :
同步和异步是指两个线程之间的关系,两个线程要么是同步或异步
同步:执行一个操作之后,等待结果,然后才继续执行后续的操作。
异步:执行一个操作后,可以去执行其他的操作,然后等待通知再回来执行刚才没执行完的操作。
阻塞和非阻塞是指一个线程处于阻塞或非阻塞
阻塞:进程给CPU传达一个任务之后,一直等待CPU处理完成,然后才执行后面的操作。
非阻塞:进程给CPU传达任我后,继续处理后续的操作,隔断时间再来询问之前的操作是否完成。这样的过程其实也叫轮询。
b :
进程:就是一个正在执行的任务
线程:是进程的一个执行路径
异步代码的分类:
1)定时器
2)事件体
3)发送请求接收响应
c :
1.程序是什么: 指示计算机每一步动作的指令
2.程序是由什么组成的: 指令和数据的组成体
3.什么是计算机语言: 计算机可以直接识别并使用的语言
4.正在执行的程序储存在什么位置:CPU中
5.什么是内存地址:内存中,用来表示命令和数据储存位置的数值
6.计算机的构成元件中,负责程序的解释和运行的是哪个:
CPU,根据程序的指令进行数据的运算,并控制整个计算机
1、浏览器将获取到的HTML代码解析成一个DOM树,HTML中的每一个标签都是DOM树中的一个节点,根节点就是document。DOM树中包含了所有的HTML标签,同时也包含了display:none 隐藏和JS动态添加的元素等
2、浏览器将所有的样式(CSS)解析成样式结构体(CSS Model),在解析过程中会去掉浏览器不识别的样式。
3、DOM Tree 和样式结构体组合后构建render tree。 render tree类似于DOM tree。但是有较大差别。render树中的每个节点都有自己的样式,但是render tree中不包含display:none的元素。但是visiblity:hidden的隐藏元素会包含在render Tree中。因为visibility:hidden会影响布局(layout),且在文档流中占据一定的空间。
4、一旦render Tree 构建完毕,浏览器就可以根据render tree绘制页面了
回流与重绘
1、什么是回流?
当render tree 中的一部分(或者全部)因为元素的规模尺寸、布局隐藏等改变需要重新构建。这就是回流。得到节点的几何信息(位置,大小)
2、什么是重绘?
在回流的时候,浏览器会使渲染树中受影响的部分失效,并重新绘制这部分的渲染树,完成回流后,浏览器会重新绘制受影响的部分到屏幕中,该过程称为重绘根据渲染树以及回流得到的几何信息,得到节点的绝对像素
3、什么情况下浏览器会发生重绘?
重绘不一定引起回流,但是回流一定会影响重绘。只是改变某些元素的属性并且这些属性会影响到元素的外观、风格,不会影响页面的布局,比如backgorund-color;color等;visability:hidden只重绘不回流
4、什么情况下,浏览器会发生回流?(重要)
当页面布局或者几何大小发生变化时就会发生回流。
①添加或删除可见的DOM元素(标签的增删);
②元素的位置变化
③元素的尺寸变化--内容区域、边框、内外边距、宽高
④内容改变--文本内容改变或者图片大小改变而引起的计算值宽度和高度改变
⑤页面渲染的初始化(这肯定避免不了)
⑥浏览器可视窗口变化---因为回流是根据视口的大小来计算元素的位置和大小的
过程:
不是修改完立马执行这个过程
浏览器会维护1个队列,把所有会引起回流、重绘的操作放入这个队列,等队列中的操作到了一定的数量或者到了一定的时间间隔,浏览器就会flush队列,进行一个批处理。这样就会让多次的回流、重绘变成一次回流重绘。
如何优化页面 (也就是减少重绘和回流)
减少回流和重绘就是减少对render tree的操作(合并多次DOM修改和样式修改),减少对一些元素style的请求。具体方法如下:
1.由于display属性为none的元素不在渲染树中,对隐藏的元素操作不会引发其他元素的重排。如果要对一个元素进行复杂的操作时,可以先隐藏它,操作完成后再显示。这样只在隐藏和显示时触发2次重排。
2.不要经常访问会引起浏览器flush队列的属性,如果确实要访问的话,可以利用缓存;也就是说需要经常去那些引起浏览器重排的属性时,需要缓存到变量中,再调用。
3.直接改变className,如果动态改变样式,可以使用cssText(利用cssText 属性合并所有改变,然后一次性写入)
一般情况下我们用js设置元素对象的样式会使用这样的形式:
element.style.cssText="width:20px;height:20px;border:solid 1px red"
http:
是用于从万维网服务器传输超文本到本地浏览器的传送协议(是基于应用层的通信规范 (超文本传输协议:通信双方都要遵守的协议)
它是基于tcp/ip协议的传输协议(http是封装了tcp/ip协议)
所谓超文本传输,传输的即是html/css/js可视化前端代码
http的特点:
支持客户/服务器模式:(Client客户端/Server服务器端)
简单快速:客户向服务器请求服务时,只需传送请求方法和路径。请求方法常用的有GET、HEAD、POST。每种方法规定了客户与服务器联系的类型不同。由于HTTP协议简单,使得HTTP服务器的程序规模小,因而通信速度很快。
灵活:HTTP允许传输任意类型的数据对象。正在传输的类型由Content-Type加以标记。
无连接:无连接的含义是限制每次连接只处理一个请求。服务器处理完客户的请求,并收到客户的应答后,即断开连接。采用这种方式可以节省传输时间。
无状态:HTTP协议是无状态协议。无状态是指协议对于事务处理没有记忆能力。缺少状态意味着如果后续处理需要前面的信息,则它必须重传,这样可能导致每次连接传送的数据量增大。另一方面,在服务器不需要先前信息时它的应答就较快。
Http的状态码:状态代码有三位数字组成,第一个数字定义了响应的类别,共分五种类别:
1xx: | 指示信息--表示成功接收请求,要求客户端继续提交下一次请求才能完成整个处理过程 |
2xx: | 成功--表示成功接收请求并已完成整个处理过程,常用200 |
3xx: | 也是成功--只不过中间做了一些额外处理,比如:请求的资源已经移动一个新地址:常用302、304、307 |
4xx: | 客户端错误--请求有语法错误或请求无法实现,请求参数错误,常用404地址错误 |
5xx: | 服务器端错误--服务器未能实现合法的请求,常用500未知服务器错误 |
http:超文本传输协议,是一个基于请求与响应,无状态的,应用层的协议,常基于TCP/IP协议传输数据,互联网上应用最为广泛的一种网络协议,所有的WWW文件都必须遵守这个标准。设计HTTP的初衷是为了提供一种发布和接收HTML页面的方法。
HTTPS:是身披SSL外壳的HTTP。HTTPS是一种通过计算机网络进行安全通信的传输协议,经由HTTP进行通信,利用SSL/TLS给数据加密。HTTPS使用的主要目的是提供对网站服务器的身份认证,同时保护交换数据的隐私与完整性。
PS:TLS是传输层加密协议,前身是SSL协议,由网景公司1995年发布,有时候两者不区分
HTTP 协议传输的数据都是未加密的,也就是明文的,因此使用 HTTP 协议传输隐私信息非常不安全,为了保证这些隐私数据能加密传输,于是网景公司设计了SSL(Secure Sockets Layer)协议用于对 HTTP 协议传输的数据进行加密,从而就诞生了HTTPS。简单来说 HTTPS 协议是由 SSL+HTTP 协议构建的可进行加密传输、身份认证的网络协议,要比http 协议安全
TCP(Transmission Control Protocol,传输控制协议)是一种面向连接的、可靠的、基于字节流的通信协议,数据在传输前要建立连接,传输完毕后还要断开连接
原型:每一个函数(一般指构造函数)都有一个prototype属性,指向一个空对象(显示原型对象),
每个实例对象都有一个__proto__属性,指向一个空对象(该类的原型对象)
原型对象里面存放着该类的实例对象所共有的方法和属性,因为是所有实例对象所共有的,就不需要每次创造实例对象的时候在此浪费内存
继承:是指子类继承父类的所有属性和方法:在es5的构造函数中,在子类里面,利用call或apply方法调用父类的构造函数并改变其this指向为子类构造函数的this,此时子类就继承了父类的私有属性和方法,在将父类的实例对象赋值给子类的原型对象,此时子类就继承了父类的原型对象和方法; 在es6的类中,利用关键字extends关键字来继承父类的构造函数,利用super来借用父类的构造方法,放在子类构造方法中的第一行
class Animal { //constructor构造方法 constructor(id, name) { this.id = id; this.name = name; } eat() { console.log("Animal eat"); } } class Student extends Animal { constructor(id, name, score) { super(id, name); //这句话必须放在第一行 this.score = score; } study() { console.log("Student study"); } } let a = new Animal(1, "武娜婷"); console.log(a); let s = new Student(2, "张艳清", 100); console.log(s); s.eat(); s.study();
call和apply的区别:每个函数都有这两个方法
共同点:在函数调用的时候,改变函数的this指向
都是针对有名函数
不同点:apply只有两个参数,第二个参数需要用 [ ] 包起来,call不用(可以有无限多个参数),
function Zi(name,age,study){ Fu.apply(this,[name,age]) this.study }
1.普通for循环
2.优化版for循环
3.forEach()循环 改变原数组
4.map()循环:不改变原数组
5.filter 不改变原数组
6.for...of..
7.for...in..
//filter map循环和filter类似,里面需要return this.arr.filter((v,i)=>{ if(v.id==this.$route.params.xiaoming){ return v } }) forEach()改变元素组 和map还有filter类似 //for…in是遍历数组 和 对象的key值 for(let i in arr){ console.log(i) // 输出下标 } //for...of 是遍历数组的value let arr=[1,2,3,4] for(let value of arr){ console.log(value) //输出的是value值 } //普通for循环 for(let i=0;arr<length;i++){} //优化版for循环:使用临时变量将长度缓存起来,避免重复获取数组长度,当数组较大时优化效果才会比较明显,这种方法基本上是所有循环遍历方法中性能最高的一种 for(let i=0,len=arr.length;i<len;i++){}
1.冒泡排序:
基本思想
外层循环决定循环的趟数 N个数比较,要比较N-1趟(每一趟才能拿出一个最大值或最小值,所以总共需要N-1趟)
内侧循环决定每趟比较的次数 每趟比较 N-1-i(次数)(每一趟中每一次要相邻的两个数两两比较,所以需要 N-1-i次)
每次进行两个数的交换
for (var i = 0; i < arr.length - 1; i++) { //控制比较的趟数 for (var j = 0; j < arr.length - i - 1; j++) { //控制每一趟比较的次数 if (arr[j] < arr[j + 1]) { //相邻元素两两对比 var t = arr[j]; //元素交换 arr[j] = arr[j + 1]; arr[j + 1] = t; } } } console.log(arr);
2.选择排序:
基本思想(按升序来说)
外层循环跑趟数:length-1趟,内层是用来擂台比较(第一个数第一趟和所有的数比较,过程中k(下标)的值一直在变,一直变成最小的),用一个变量记录最小值得下标,一趟比较完,就是外循环进行一次,交换一次,交换第一个数和最小下 标对应的值
for(var i=0; i<arr.length-1;i++){ var k = i; for(var j=i+1; j < arr.length; j++){ if(arr[k]>arr[j]){ k = j; } } t = arr[i]; arr[i] = arr[k]; arr[k] = t; } console.log(arr);
3.冒泡和选择的区别:
(1)两者外层循环都指的是总共比较的n-1趟
(2)而冒泡的内层循环是相邻的两个数两两比较,而选择排序是第一个数字不停的和别的数字比较,将比较出的最大值和最小值结果放到第一个,然后在和别的数继续比较
(3)冒泡排序每一轮比较后,位置不对都需要换位置,选择排序每一轮比较都只需要换一次位置;
(4)冒泡排序是通过数去找位置,选择排序是给定位置去找数;
冒泡排序优缺点:
优点:比较简单,空间复杂度较低,是稳定的;
缺点:时间复杂度太高,效率慢;
选择排序优缺点:
优点:一轮比较只需要换一次位置;
缺点:效率慢,不稳定(举个例子5,8,5,2,9 我们知道第一遍选择第一个元素5会和2交换,那么原序列中2个5的相对位置前后顺序就破坏了)。
1.箭头函数:
定义箭头函在数语法上要比普通函数简洁得多。箭头函数省去了function关键字,采用箭头=>来定义函数。函数的参数放在=>前面的括号中,函数体跟在=>后的花括号中。
关于箭头函数的参数:
① 如果箭头函数没有参数,直接写一个空括号即可。
② 如果箭头函数的参数只有一个,也可以省去包裹参数的括号。
③ 如果箭头函数有多个参数,将参数依次用逗号(,)分隔,包裹在括号中即可。
关于箭头函数的函数体:
①如果箭头函数的函数体只有一句代码,就是简单返回某个变量或者返回一个简单的JS表达式,可以省去函数体的大括号{ }。
②如果箭头函数的函数体只有一条语句并且不需要返回值(最常见是调用一个函数),可以给这条语句前面加一个void关键字
箭头函数(不会创建自己的this)中的this实际是继承的它定义时所处的 全局执行环境(外层执行环境)中的this,所以指向Window对象,箭头函数继承来的this指向永远不变
2.箭头函数和普通函数的区别
1.写法不同:箭头函数使用箭头定义,普通函数中没有
2.箭头函数都是匿名函数:普通函数可以有匿名函数,也可以是具名函数
3.箭头函数不能用于构造函数:因为箭头函数不会定义this,箭头函数的this指的是外层执行环境的this,且不会改变,这样子导致构造函数new出来的对象,调用时会报错
4.this指向不同:在箭头函数中this指定义时外层执行环境的this,而在普通函数中指调用该函数的对象,在构造函数中,指new出来的对象
5.箭头函数没有arguments对象:每一个普通函数都有一个arguments对象,用来存储实际参数(将其放到一个伪数组 )
6.其它区别:箭头函数,没有prototype原型对象,没有super,没有new.target
内存泄露:是指程序中已动态分配的堆内存由于某种原因程序未释放或无法释放,直到浏览器进程结束。造成系统内存的浪费,导致程序运行速度减慢甚至系统崩溃等严重后果
哪些操作会造成内存泄露
1.意外的全局变量引起的内存泄露
2.闭包引起的内存泄露(全局变量会占用内存,造成泄露)
3.没有清理的DOM元素引用
4.被遗忘的定时器或者回调(未关闭)
5.子元素存在引起的内存泄露
避免内存泄露:
1.避免误建全局变量,尽量少使用全局变量
2.使用完定时器记得关闭
注:
1.在new出来新对象时,系统会在堆内存开辟分配空间,
2.垃圾回收机制:系统会周期性的检查空间,当没有任何一个引用指向该对象时,就会自动将堆开辟的空间进行释放(比如 new Function:凭空出现的,就会被销毁)(但是这个过程不是实时的,因为其开销比较大,所以垃圾回收系统(GC)会按照固定的时间间隔,周期性的执行。)
拷贝是用一个已有对象去初始化一个新的对象
深拷贝是:修改新变量的值,不会影响原有变量的值
浅拷贝是:修改新变量的值,会影响原有变量的值
深浅拷贝一般是针对引用类型,引用类型在内存中有两个空间,一个是栈空间存放地址,一个是堆空间存放数据;浅拷贝是只拷贝引用地址,不开辟空间,深拷贝是开辟空间且赋值
ES6解构是快速取出数组和对象的值
//1.数组中的 解构赋值 let [a,b,c]=["我是a","我是b","我是c"] console.log(a) //我是a console.log(b) //我是b console.log(c) //我是c //1.数组解构 let a,b,c,rest [a,b,c]=["我是a","我是b","我是c"] console.log(a) //我是a console.log(b) //我是b console.log(c) //我是c //1.数组解构 [a,b,...rest]=["aa","bb","cc","dd","ee"] console.log(a) //"aa" console.log(b) //"bb" console.log(rest) //["cc","dd","ee"],就是将剩余的数据当成一个数组或对象 //2.对象中的解构 let {name,age}={name:"张艳清",age:18} console.log(name) //张艳清 console.log(age) //18 //2.对象中的解构:一定要用一对小括号包裹解构赋值语句,花括号不允许出现在赋值语句左侧,添加小括号后可以将块语句转化为一个表达式 let name,age ({name,age}={name:"张艳清",age:18}) console.log(name) //张艳清 console.log(age) //18 //2.对象的解构 ({name,age,...rest}={name:"张艳清",age:18,love:"money",eat:"好吃的"}) console.log(name) //张艳清 console.log(age) //18 console.log(rest) //{love:"money",eat:"好吃的"} //2.对象的解构 let [a,...b]=[1,2,3] console.log(a) //1 console.log(b) //[2,3] //3.字符串解构 let str="123nihao" let [a,b,c,d,e,f]=str console.log(a,b,c,d,e,f) //1 2 3 n i h //4.从函数返回值解构 function f(){ return [1,2] } let a,b [a,b]=f() console.log(a) //1 console.log(b) //2
ES6解构是浅拷贝
扩展运算符是什么
对象中的扩展运算符 三个点(...) :用于取出参数对象中的所有可遍历属性,拷贝到当前对象中(扩展运算符就是将数据展开:将原数据里面的内容搬到新数据里面)
ES6扩展运算符:浅拷贝
let obj={a:1,b:2} let obj2={...obj} //将数据里面的内容搬到新数据里面,所以还需要花括号这些符号 console.log(obj2) //{a:1,b:2} //扩展运算符也用于改变react的redux中的state对象里面的某一个数据 let obj={a:1,b:2,c:3} let obj2={...obj,c:8} console.log(obj2) //{a:1,b:2,c:8}
扩展运算符有什么用
//0.将字符串转为数组 let str=[..."hello"] console.log(str) //['h','e','l','l','o','w'] //1.复制展开数组或对象 let obj={a:1,b:2} let obj2={...obj} console.log(obj2) //{a:1,b:2} //2.合并数组 let arr=[1,2,3] let arr1=[4,5,6] let arr2=[...arr,...arr1,7,8] console.log(arr2) //[1,2,3,4,5,6,7,8] //3.跟函数参数结合:就是声明一个变量时是数组,将该变量以实参的形式传到函数形参里面,可以借用扩展运算符 //4.在对象中使用时:如果放到最后,同key的话会覆盖前面的值 let obj={a:1,b:2} let obj1={a:3,b:4} let obj2={...obj,...obj1} console.log(obj2) //{a:3,b:4}
性能优化的目的
1.从用户角度而言,优化能够让页面加载得更快,对用户的操作响应得更及时,能够给用户提供更为友好的体验。
2.从服务商角度而言,优化能够减少页面请求数,或者减小请求所占带宽,能够节省可观的资源。
1.利用浏览器缓存你的js和css文件:
在网站根目录.htaccess中加入以下代码
ExpiresActive on
ExpiresDefault “access plus 1 year”
这段代码的意思是对 jpg|gif|png|css|js 发送herder缓存头,进行一年的缓存、在浏览器不使用ctrl+F5强制刷新时,会一直缓存到时间结束,唯一遗憾的是如果更改了js或者css文件必须把以前的路径或者文件名更改,可以这样base.js?ver=(x) 这种方式下次浏览器就会自动读取并缓存
2.把你的.js库文件地址替换成Google CDN(内容分发网络)的地址
减少传输距离,缩短请求时间
3.精简和优化你的js和css
js,css,文件中一般存在大量的空格,换行,注释,将其压缩掉,则有利于网络传输
4.压缩你的js和css文件
将js和css文件进行GZIP压缩,可以减少30%以上的体积(服务端开启GZIP ,对用户请求的页面进行压缩处理,以达到节省网络带宽,提高浏览网站速度的作用)
5.减少重复的http请求:
比如可以将许多图片合成为一个单独的图片(精灵图),然后可以通过background-position属性来改变北京图片的位置
或者合并文件:将把所用到的 css 样式或者 js 可以封装成一个公共类)
let xhr=new XMLHttpRequest() //1.实例化一个XMLHttpRequest对象 xhr.open("get","ajax.txt",true) //2.设置请求参数xhr.open(请求类型(post还是get),地址(发送给谁),是否异步) xhr.send() //3.发送请求 xhr.onreadystatechange=function(){ //4.等待服务器的响应 if(xhr.status==200&&xhr.readyState==4){ //5.当小黄人的状态吗为4时,http协议为200时 console.log(xhr.responsText) //6.获得后端传来的数据 } }
http常见状态码
1xx: | 指示信息--表示成功接收请求,要求客户端继续提交下一次请求才能完成整个处理过程 |
2xx: | 成功--表示成功接收请求并已完成整个处理过程,常用200 |
3xx: | 也是成功--只不过中间做了一些额外处理,比如:请求的资源已经移动一个新地址:常用302、304、307 |
4xx: | 客户端(前端)错误--请求有语法错误或请求无法实现,请求参数错误,常用404地址错误 |
5xx: | 服务器端错误--服务器未能实现合法的请求,常用500未知服务器错误 |
301 Moved Permanently 永久性转移/重定向,一般应用于网站域名更换,访问老域名,永久都跳转到新的域名上
302 Move Temporarily 临时转移
304 Not Modified 读取的是缓存中的数据,这个是客户端和服务器端共建的协商缓存(把不经常更新,请求过的资源文件做缓存,后期在访问这些资源直接走缓存数据,除非服务器端更新了此资源,或者客户端强制清缓存刷新等
307 Temporary Redirect 临时重定向,一般应用于服务器的负载均衡.
400 Bad Request 请求参数错误
401 Unauthorized 无权限访问
404 Not Found 地址错误
405 Method Not Allowed 当前请求的方式服务器不支持
500 Internal Server Error 未知服务器错误
503 Service Unavailable 服务器超负荷
预加载:提前加载图片,当用户需要查看时可直接从本地缓存中渲染。预加载是牺牲服务器前端性能,换取更好的用户体验,这样可以使用户的操作得到最快的反映
懒加载:也叫延迟加载,按照一定的条件或需求等到满足条件的时候在加载对应的资源。懒加载页面加载速度快、可以减轻服务器的压力、节约了流量,用户体验好
实现要点:将图片的src设为空,或者也可以将所有图片的src设一个底图,当图片还没加载完时,用这张底图来占图片的位置,防止页面结构混乱。再给一个自定义的data-url属性,用来存放图片的真实路径。lazyload属性用来标明哪些图片是需要懒加载。监听滚动事件,只在图片出现在可视区时,才动态地将图片的真实地址赋予图片的src属性。
什么时候使用预加载:
在网页全部加载之前,对一些主要内容进行加载,以提供给用户更好的体验,减少等待的时间。否则,如果一个页面的内容过于庞大,没有使用预加载技术的页面就会长时间的展现为一片空白,直到所有内容加载完毕。
注:页面加载过程:
如果页面是第一次访问,浏览器向服务器http请求后,服务器返回html文件,在整个页面加载过程中,总的来说是按顺序从上到下执行,这是基于js的单线程机制,但是html和css是并行加载的,html生成dom树,css生成rule树,两者相结合生成render树。
接下来遇到js文件,则会造成堵塞,页面会一直等到js文件执行完才会进行下一步操作。
在进行html中body部分加载时,如果遇到图片的src,它会请求资源,此时图片还没下载完全,在页面上并不会留下图片的位置,而html不会堵塞,将会继续执行下去。
等到有图片请求下载完成,html又会重新渲染页面,将图片显示出来。
1.获取DOM元素 / 节点
方法 | 描述 |
document.getElementById("ID名" ) | 返回带有指定ID的DOM节点 |
document.getElementsByTagName("标签名" ) | 批量返回带有指定标签名的DOM节点存储到数组里 |
document.getElementsByClassName("类名" ) | 批量返回带有指定类名的DOM节点存储到数组里 |
document.getElementsByName( "name名") | 批量返回带有指定name的DOM节点存储到数组里 |
document.querySelectorAll("选择器") | 批量返回带有指定选择器的DOM节点存储到数组里 |
document.querySelector("选择器") | 获取单个指定选择器的DOM元素,ID,类,标签 |
2.创建DOM元素
document.createElement(HTML标签名) | 创建一个元素节点 |
document.createTextNode(文字) | 创建文本节点 |
document.createAttribute(属性名) | 创建了一个属性(节点) |
3.添加DOM节点
父节点.appendChild(子节点) | 将子节点插入到父节点的末尾 |
父节点.insertBefore(目标节点,参照节点) | 将目标节点插入值参照节点之前如果参照节点为null,等价于插入到最后/appendChild |
4.删除DOM节点
父节点.removeChild(子节点) | 删除子节点 |
父节点.replaceChild(newChild, oldChild) | 用newChild节点替换oldChild节点 |
5.DOM节点间的相互访问(只包括元素节点,不包括文本)
节点.firstElementChild | 返回节点的第一个子节点 |
节点.lastElementChild | 返回节点的最后一个子节点 |
节点.nextElementSibling | 返回节点的下一个节点 |
节点.previousElementSibling | 返回节点的上一个节点 |
节点.children | 返回该父元素的所有元素子节点,放到一个数组里面 |
节点. parentNode | 返回节点的父节点 |
6.DOM节点的属性的操作
DOM节点.getAttribute("属性名") | 通过属性名称获取某个节点属性的值 |
DOM节点.setAttribute("属性名","属性值"); | 修改节点的属性的值 |
DOM节点.removeAttribute(name) | 删除节点的某个属性 |
7.DOM节点的替换
父节点.replaceChild(newChild, oldChild) | 用newChild节点替换oldChild节点 |
8.给DOM节点插入内容
节点.innerHTML='内容' | 给节点插入内容 |
1、基本选择器
1)ID选择器:$("#box1").css("backgroundColor","red");//js写法
2)类选择器:$(".box").css({backgroundColor:"blue"});//css写法
3)标签选择器:$("p").css({backgroundColor:"yellow"});
4)群组选择器:$("span,div").css({backgroundColor:"green"});
5)通用选择器:$("*").css({backgroundColor:"black"});
2、层次选择器
1)子代选择器:$("body>div").css({backgroundColor:"red"});
2)后代选择器:$("body #box1").css({backgroundColor:"blue"});
3)相邻选择器:$("#box2+div").css({backgroundColor:"green"});
4)兄弟选择器:$("#box2~div").css({backgroundColor:"yellow"});
3、属性选择器
1)通过属性名来获取元素:$("div[class名]").css({backgroundColor:"red"});
2)组合属性名:$("div[class名][id]").css({backgroundColor:"blue"});
3)属性名指定属性值:$("div[id=box1]").css({backgroundColor:"green"});
4)属性是以某些值开始的元素 ^:$('input[name^=username]').css('background','gray');
5)属性是以某些值结尾的元素 $:$('input[name$=222]').css('background','green');
6)属性是以包含某些值的元素 * :$('button[class*=danger]').css('background','orange');
4、伪类选择器:过滤、在该包装集中在筛选一遍
1)even:获取偶数行的元素li:$("li:even").css({backgroundColor:"red"});
2)odd:获取奇数行的元素:$("div:odd").css({backgroundColor:"yellow"});
3)eq(n):根据下标返回jQueryDom对象节点:
a)$("div").eq(3).css({backgroundColor:"blue"});
b)$("div:eq(2)").css({backgroundColor:"blue"});
c)let n = 2; $("div:eq("+n+")").css({backgroundColor:"green"});
4)first:第一个元素div:$("div:first").css({backgroundColor:"green"});
5)last:最后一个li:$("li:last").css({backgroundColor:"green"});
6)not(元素):除了某个元素:
a)$("div:not('#box2')").css({backgroundColor:"greenyellow"});
b)$("div").not('#box2').css({backgroundColor:"yellowgreen"});
7)gt(n):大于但不包含某个元素:
a)$("div:gt(2)").css({backgroundColor:"red"});
b)$("div:gt("+n+")").css({backgroundColor:"red"});
8)lt(n):小于但不包含某个元素:
a)$("div:lt(2)").css({backgroundColor:"red"});
b)$("div:lt("+n+")").css({backgroundColor:"red"});
5、内容选择器
1)contains:根据内容选择包含:$("div:contains('1')").css({backgroundColor:"red"});
2)empty:选择内容为空的元素:$("div:empty").css({backgroundColor:"blue"});//注意文本节点
3)has(目标元素):选择包含目标元素的元素:
a)$("div:has('span')").css({backgroundColor:"red"});
b)$("div").has('span').css({backgroundColor:"red"});
6、可见性选择器
1)hidden:选中隐藏的元素:$("div:hidden").css({backgroundColor:"yellow"});
2)visible:选中显示的元素:$("div:visible").css({backgroundColor:"yellow"});
before(): $('div').before($('span')) | div的前面是span=把span插到div前面 |
after(): $('div').after($('span')) | div的后面是span=把span插到div的后面 |
insertBefore(): | 把要插入节点插入到指定节点的前面 |
insertAfter (): | 把要插入的节点插入到指定节点的后面 |
append(): $('div').append($('span')) | div子节点的末尾是span=把span插到div子节点的末尾 |
appendTo () | 把指定节点添加到指定父级里面的最后面 |
prepend () | 在指定父级里面的最前面添加指定节点 |
prependTo(): $('div').prependTo($('span')) | div子节点的首位是span=把span插到div子节点的首位 |
remove(): $('div').remove() | 删除div节点:返回值是被删除的节点 不会保留之前的事件和行为 |
detach(): $('div').detach() | 删除div节点:返回值是被删除的节点,会保留之前的事件和行为 |
$("<div></div>") | 创建节点 |
${变量} | ES6模板字符串` ` |
函数节流:触发高频事件,n秒内函数只会执行一次,节流会稀释函数的执行频率
函数防抖:触发高频事件后,n秒内函数只会执行一次,执行的是n秒内最后一次被触发时的事件(基本思路就是把多个信号合并为一个信号)
共同点:函数节流(throttle)与 函数防抖(debounce)都是为了限制函数的执行频次,以优化函数触发频率过高导致的响应速度跟不上触发频率,出现延迟,假死或卡顿的现象。
区别: 函数节流不管事件触发有多频繁,都会保证在规定时间内一定会执行一次真正的事件处理函数,而函数防抖只是在 规定时间内 最后一次触发事件后 才执行一次函数。
应用场景:函数节流:比如在页面的无限加载场景下,我们需要用户在滚动页面时,每隔一段时间发一次 Ajax 请求,而不是在用户停下滚动页面操作时才去请求数据。这样的场景,就适合用节流技术来实现。
函数防抖:给要触发的事件绑定一个延迟执行,如果n(规定时间内)秒内事件被再次触发,那么就先清除延迟执行定时器,然后定时器重新计算时间,当n(规定时间内)秒内没有再次被触发该事件,那么再去执行代码(简化理解:你一次又一次发送请求,哪次请求完 间隔了5(规定时间)秒都没有再次发送,那么我就真正的帮你发送请求)
1.post的安全性高于get;
如果以get方式请求,请求参数会拼接到url后面,安全性性低,以post方式请求,请求参数会包裹在请求体中,安全性更高,第2点:get会将数据(这里指静态资源:图片,页面等)缓存起来,而post不会,这样也会使得个体请求数据更快一些
2.数量区别:
get方式传输的数据量小,规定不能超过2kb,post方式请求数据量大,没有限制。
3.传输速度:
get的传输速度高于post:1.get请求数据只需一次性,post需要两次;2.get会将请求到的数据缓存
因为使用方法相同,因此只要改变jQuery函数,就可以将程序在GET请求和POST请求之间切换
4.缓存性:
get请求是可以缓存的,post请求不能缓存
5.数据类型:
post能发送更多的数据类型
get只能发送ASCII字符
5.数据包
GET产生一个TCP数据包;POST产生两个TCP数据包。对于GET方式的请求,浏览器会把http header和data一并发送出去,服务器响应200(返回数据);而对于POST,浏览器先发送header,服务器响应100 continue,浏览器再发送data,服务器响应200 ok(返回数据)。在网络环境好的情况下,发一次包的时间和发两次包的时间差别基本可以无视。而在网络环境差的情况下,两次包的TCP在验证数据包完整性上,有非常大的优点。并不是所有浏览器都会在POST中发送两次包,Firefox就只发送一次。这也是get快,post慢的原因
CSRF:Cross Site Request Forgery(跨站点请求伪造):
CSRF 攻击者在用户已经登录目标网站之后,诱使用户访问一个攻击页面,利用目标网站对用户的信任,以用户身份在攻击页面对目标网站发起伪造用户操作的请求,达到攻击目的 (一个场地上有一个房子A,一个人来到这个场地,把他引诱到A房子,那么从A房子出来的消息会被认为是这个人发出的
如下:其中Web A为存在CSRF漏洞的网站,Web B为攻击者构建的恶意网站,User C为Web A网站的合法用户。
CSRF 攻击原理
通过访问恶意网址,恶意网址返回来js自动执行访问你之前登陆的网址,因为你已经登录了,所以再次访问将会携带cookie,因为服务器只认有没有cookie,无法区分是不是用户正常的访问,所以会欺骗服务器,造成伤害
如何避免CSRF攻击:
预防csrf攻击简单可行的方法就是在客户端网页上再次添加一个cookie,保存一个随机数,而用户访问的时候,先读取这个cookie的值,hash一下这个cookie值并发送给服务器,服务器接收到用户的hash之后的值,同时取出之前设置在用户端的cookie的值,用同样的算法hash这个cookie值,比较这两个hash值,相同则是合法。(如果用户访问了病毒网站,也想带这个cookie去访问的时候,此时,因为病毒网站无法获取第三方cookie的值,所以他也就无法hash这个随机数,所以也就会被服务器校验的过滤掉)
1.基本数据类型:
数值number:包含数字和NaN
字符串string:由单双引号包裹的内容
布尔值boolean:true/ false
undefined:变量声明但未赋值
null:变量声明且被赋值为null空
symbol:表示独一无二的值,ES6新增
2.引用类型:
object:对象
array:数组
function:函数
3.检测数据类型
typeof 后面加变量名,typeof 本身是字符串类型
instanceof 运算符需要指定一个构造函数,或者说指定一
个特定的类型,它用来判断这个构造函数的原型是否在给定对象的
原型链上(123 instanceof Number, //false)
typeof 123, //"number" typeof 'dsfsf', //"string" typeof false, //"boolean" typeof [1,2,3], //"object" typeof {a:1,b:2,c:3}, //"object" typeof function(){console.log('aaa');}, //"function" typeof undefined, //"undefined" typeof null, //"object" typeof new Date(), //"object" typeof /^[a-zA-Z]{5,20}$/, //"object" typeof new Error() //"object" 123 instanceof Number, //false 'dsfsf' instanceof String, //false false instanceof Boolean, //false [1,2,3] instanceof Array, //true {a:1,b:2,c:3} instanceof Object, //true function(){console.log('aaa');} instanceof Function, //true undefined instanceof Object, //false null instanceof Object, //false new Date() instanceof Date, //true /^[a-zA-Z]{5,20}$/ instanceof RegExp, //true new Error() instanceof Error //true
//1.数组拷贝 let arr=[1,2,3,4,5] let newarr=[] for(let i=0;i<arr.length;i++){ if(newarr.indexOf(arr[i])==-1){ newarr.push(arr[i]) } } console.log(newarr) //2.面试够用版 重点 function kaobei(obj){ //该函数封装深拷贝 if(obj &&typeof obj=="object"){ //判断该数据是否存在 和 是否是引用数据类型 let newobj=Array.isArray(obj)?[]:{} //定义一个新的变量,如果传入的函数是数组,那么新定义的变量就是空数组,如果旧变量是对象,那么新变量就是对象 for(let key in obj){ //如果该key的value值是对象,则递归调用深拷贝方法进行拷贝 newobj[key]=typeof obj[key]=="object"?deepCopy(obj[key]):obj[key] } }eles{ let newobj=obj } return newobj } //注: obj.hasOwnProperty(属性):该方法返回一个布尔值,判断该对象时否有某个属性,但不会去查找他的原型链 deepCopy():引用数据的 深拷贝:newobj=deepCopy(obj) obj.constructor=类 实例化对象.constructor属性 可以用来判断某对象是否由某个函数(类)实例化得来 obj.constructor=Array?[]:{} 判断该实例化对象时否是数组 fn.constructor==Function arr.constructor==Array obj.constructor==Object //3.使用JSON.parse() 和 JSON.stringify()这两个方法完成深拷贝 let obj={ name:"张艳清", age:23, love:"男" } let newobj=JSON.parse(JSON.stringify(obj)) console.log(newobj) //注: JSON.stringify()://将JSON对象转为JSON字符串 JSON.parse(): //将JSON字符串转为JSON对象 该克隆方法有缺陷,当对象属性是不可序列化是,就会存在数据丢失的风险
递归:一个函数直接或间接调用自己本身
递归必须具备两个条件,一个是调用自己,一个是有终止条件,并且终止条件必须是在递归最开始的地方
let num=0 function add(){ if(num<10){ console.log(num++) } add() } add()
递归的优缺点:
优点:
1、代码简洁
2、易于理解
缺点:
1、时间和空间的消耗比较大
递归由于是函数调用自身,而函数的调用时消耗时间和空间的,每一次函数调用,都需要在内存栈中分配空间以保存参数,返回值和临时变量,而往栈中压入和弹出数据也都需要时间,所以降低了效率。
2、重复计算--效率低
递归中又很多计算都是重复的,递归的本质时把一个问题分解成两个或多个小 问题,多个小问题存在重叠的部分,即存在重复计算,如斐波那契数列的递归实现。
3、调用栈溢出---性能差
递归可能时调用栈溢出,每次调用时都会在内存栈中分配空间,而栈空间的容量是有限的,当调用的次数太多,就可能会超出栈的容量,进而造成调用栈溢出。
1、拷贝:是指:用一个已有的对象初始化一个新的对象
2、深浅拷贝是针对于引用类型
3、引用数据类型在内存中存储是有俩个空间,堆空间存储数据,栈空间存堆空
间的地址(变量)
4、浅拷贝是:只拷贝引用地址,不开辟空间:两把钥匙,一个仓库
深拷贝是:开辟空间并且赋值,两把钥匙,两个仓库之间互不影响
5、什么时候用浅拷贝:从服务器fetch 到数据之后我将其存放在 store 中,通过 props 传递给界面,然后我需要对这堆数据进行修改,那涉及到的修改就一定有保存和取消,所以我们需要将这堆数据拷贝到其它地方。
6、什么时候用深拷贝:当你想使用某个对象的值,在修改时不想修改原对象,那么可以用深拷贝弄一个新的内存对象。像es6 的新增方法都是深拷贝,所以推荐使用es6 语法。
多维数组:实际是一维数组的嵌套
//第一种:二维数组的循环 let arr=[[1,2,3],[4,5,6],[7,8,9]] if(arr.length!=0){ for(let i=0;i<arr.length;i++){ //循环最外面的数组 for(let j=0;j<arr[i].length;j++){ //循环里面的每一个数组 consle.log(arr[i][j],<br/>) } } } //第二种:多维数组的遍历 let arr=[[1,3],[4,5,[6,7[8,9]]],10] function shubian(arr){ for(let key in arr){ if(arr[key].constructor==Array){ shubian(arr[key]) // 递归遍历 }else{ console.log(arr[key]) } } } shubian(arr) //第三种:多维对象的遍历,借助递归 let obj={ one:{a:1,b:2,{c:3,d:4}}, two:{e:5,f:6}, three:{g:7,h:8} } function bianli(obj){ for(let key in obj){ if(typeof obj[key]=="object"){ bianli(obj[key]) // 递归遍历 }else{ console.log(obj[key]) } } } bianli(obj)
宏任务:整体代码script,setTimeout, setInterval
微任务:Promise.then(非new Promise)
1.JavaScript语言的运行机制,也就是JavaScript代码的执行顺序
2.Event Loop机制是javascript的执行机制(上图循环的这种状态就称为事件循环机制Event Loop)
3.代码阻塞:JS语言是单线程,意味着所有的任务都需排队,前一个任务结束,才会执行后一个任务。如果一个任务耗时很长,后一个任务就需要一直等待
6.JavaScript是个单线程语言,会造成程序阻塞,所以需要异步,所以我们通过事件循环(event loop),实现代码的异步执行,事件循环的代码具体怎么执行?
a:首先,整体的script(作为第一个宏任务)开始执行的时候,会把所有代码分为同步任务、异步任务两部分
b:同步任务会直接进入主线程依次执行
c:异步任务会再分为宏任务和微任务
d:宏任务进入到Event Table中,并在里面注册回调函数,每当指定的事件完成时,Event Table会将这个函数移到Event Queue(事件队列)中
e:微任务也会进入到另一个Event Table中,并在里面注册回调函数,每当指定的事件完成时,Event Table会将这个函数移到Event Queue(事件队列)中
f:当主线程内的任务执行完毕,主线程为空时,会检查微任务的Event Queue(事件队列),如果有任务,就全部执行,如果没有就执行下一个宏任务
g:上述过程会不断重复,这就是Event Loop机制,比较完整的事件循环
什么是数组扁平化:就是将一个多维数组转换成一个一维数组
// 1. for..of: 遍历数组的value let arr = [1,2,[3,4,[5,6]]] let newarr=[] function f(arr){ for(let val of arr){ if(typeof(val)=="number"){ newarr.push(val) }else{ f(val) } } return newarr } f(arr) //2.reduce()
系统会周期性的检查空间,当没有任何一个引用指向该对象时,就会自动将堆开辟的空间进行释放(比如 new Function:凭空出现的,就会被销毁)(但是这个过程不是实时的,因为其开销比较大,所以垃圾回收系统(GC)会按照固定的时间间隔,周期性的执行。)
Nodejs 是一个基于Chrome JavaScript 运行时建立的平台,用于方便地搭建响应速度快、易于扩展的网络应用。Node 使用事件驱动,非阻塞I/O 模型而得以轻量和高效,非常适合在分布式设备上运行数据密集型的实时应用。
ssh-keygen -t rsa -C "xxxxx@xxxxx.com" 生成SSH 密钥
git init 初始化仓库
git status 查看仓库状态
git add <文件名> 将工作区的某一个文件提交到缓冲区
git add -A 将工作区的所有被修改过的和新添的和删除的操作全部提交到缓冲区
git commit -m "注释" 将缓冲区内的文件提交到版本库
git diff <文件名> 对比文件
git commit -am "注释" 将工作区中所有被追踪并且有过修改的文件一次性提交
到版本库
git log 查看提交记录
git reflog 查看提交记录(包含所有回滚)
git reset --hard <版本号> 回到过去/回到未来
git push 将本地版本库中的文件状态推送到远程库中
git pull 将远程库的状态更新到本地库中
git clone 将远程库拉取到本地
概念:
BOM 是浏览器对象模型,提供了独立于内容而与浏览器窗口进行交互的对象。
DOM 是文档对象模型,DOM 和文档有关,这里的文档指的是网页,也就是HTML 文档
标准:
BOM 没有相关标准:由于没有标准,不同的浏览器实现同一功能,可以需要不同的实现方式o DOM 是W3C 的标准
根本对象:
BOM 的最根本对象是window
DOM 最根本对象是document(实际上是window.document)
基于连接与无连接;
对系统资源的要求(TCP 较多,UDP 少);
UDP 程序结构较简单;
流模式与数据报模式;
TCP 保证数据正确性,UDP 可能丢包,TCP 保证数据顺序,UDP 不保证。
相同点:
都是循环遍历数组中的每一项
forEach和map 方法里每次执行匿名函数都支持3 个参数,参数分别是 item(当前每一项)、index(索引值)、arr(原数组)o 匿名函数中的this 都是指向window o 只能遍历数组
不同点:
orEach()没有返回值,map() 有返回值,可以return 出来 不管是forEach 还是map 在IE6-8 下都不兼容(不兼容的情况下在Array.prototype 上没有这两个方法)
回调函数callback:被作为实参传入另一函数,并在该外部函数内被调用,用以来完成某些任务的函数。如setTimeOut,ajax 请求,readFile 等。
事件发布订阅:当一个任务执行完成后,会发布一个事件,当这个事件有一个或多个‘订阅者’的时候,会接收到这个事件的发布,执行相应的任务,这种模式叫发布订阅模式。如node 的events,dom 的事件绑定
Promise:Promise 是es6 提出的异步编程的一种解决方案。
Promise 对象有三种状态:
pending: 初始状态,既不是成功,也不是失败状态。
fulfilled: 意味着操作成功完成
rejected: 意味着操作失败。
promise 的状态只能从pending 变成fulfilled,和pending 变成 rejected,状态一旦改变,就不会再改变,且只有异步操作的结果才能改变promise 的状态。
检查缓存
DNS 解析
TCP 连接
发送HTTP 请求
服务器处理请求并返回HTTP 报文
浏览器解析渲染页面
连接结束
首先在浏览器地址栏中输入url
浏览器先查看浏览器缓存-系统缓存-路由器缓存,如果缓存中有,直接显示
页面内容;如果没有,跳到第三步;
域名解析,获取相应的IP 地址
浏览器向服务器发送tcp 连接,与浏览器建立三次握手
握手成功后,建立http 请求
服务器收到请求,将数据返回至浏览器
浏览器收到http 响应
读取页面内容,浏览器渲染,解析html 源码
从浏览器中创建XMLHttpRequests
node.js 创建http 请求
支持Promise API
拦截请求和响应
转换请求数据和响应数据
取消请求
自动换成json
axios 中的发送字段的参数是data 跟params 两个
两者的区别在于params 是跟请求地址一起发送的,data 的作为一个请求体进行发送;params 一般适用于get 请求;data 一般适用于post put 请求
357642662huhu
数据驱动和组件化
数据驱动:视图随着数据的改变而改变
组件化:将一些复用的功能模块封装成组件,可以提高代码的复用性,也方便后期的维护
定义:vue是目前最为主流的MVVM框架,就是将视图和数据分离开,可以使得我们更专注于业务功能的开发
优点:耦合性低,复用性高,轻量级,高效率,简单易学,无需大量操作DOM
开发目的:解决数据绑定的问题,vue.js的主要目的是为了开发大型单页面应用,支持组件化,提高页面的复用性
核心:数据驱动和组件化
vue的单向数据流指的是组件之间的传值,规定数据只能从父组件传给子组件,而不能逆向、跨组件,或者同胞之间传
键盘:up donw left right ctrl spance enter
事件:stop阻止事件冒泡,capture让事件捕获,self只触发自己 不触发子元素,once 只触发一次,prevent阻止浏览器默认行为
两者都是向页面插值,
v-text:是指令
{{}}:是es6模板插值,当数据过大,网速不好,渲染页面时容易出现屏幕闪动,给最大的元素添加v-calok指令,然后属性选择器选中,添加“display:none”
可以,中间用逗号隔开
vue for循环中,必须使用key=唯一标识,一般是数据的id号,唯一 标识的目的是可以帮我们精准定位到某一个元素和数据,这样就方便了我们进行增删查改,而不需要整体刷新页面
是vue中带有计算功能的一个属性,在data的数据发生改变时,会重新计算,并返回一个新的数据
单页面指的是:只有一个html页面:浏览器一开始要加载所有必须的 html, js, css。所有的页面内容都包含在这个所谓的主页面中,所有跳转方式都是通过组件切换完成的
优点:
1、用户体验好,快,页面切换时,更加流畅,内容的改变不需要重新加载整个页面,对服务器压力较小。
2、前后端分离,比如vue项目
3、完全的前端组件化,前端开发不再以页面为单位,更多地采用组件化的思想,也使得代码的复用性达到更高,代码结构和组织方式更加规范化,便于修改和调整;
缺点:
1、低版本不支持
2、首次加载页面时,因为要加载大量的静态页面,时间过长
3、浏览器不支持单页面的导航,所以有需求需要自己写
4、SEO(搜索引擎优化)优化不好
SEO:
只要存在搜索的地方,就存在SEO:SEO的宗旨是如何最优化的把搜索结果呈现给有需求的网民
vuex是专门为vue开发的一个数据管理工具,将项目的所有数据放到一个类似于仓库的地方,那个组件需要,可以直接拿取,免去了组件之间传值的复杂性
在项目中store文件夹中有index.js文件,其中state是存放数据,mutations是存放改变state数据的函数方法,actions是存放请求数据的函数方法,gettres是计算属性,modules是存放模块,便于数据的管理,
一般用于单页面中组件之间的数据流通
声明式:<router-link to="">导航<router-link>
编程式:this.$router.push()
跨域是因为浏览器的安全机制,也就是同源策略 同端口号,同协议,同域名,不是同一个地方出来的是不允许交互的,为了本网站的数据安全,也就造成了跨域的出现(本地代码一般是通过浏览器访为服务器的)
第一种:利用本地开发着服务器devServe代理跨域,(利用脚手架给vue内置的微型服务器进行代理跨域)
步骤:1.在项目跟路径下新建 vue.config.js文件(vue的webcat的配置文件),
2.proxy:{} proxy是属于devserve容器的,proxy对象里面是一个解决跨域的一个地址,修改里面的地址参数
module.exports={ devServer:{ open:true,//自动开启浏览器 port:8888, //修改端口 proxy:{ "/api":{ target:"http://www.weather.com.cn", changeOrigin:true, "pathRewrite":{ "^/api":"/" } } }, } }
3.将组件中的请求地址替换成/api
4.重启项目
第二种:后端使用CORS解决跨域, 在后端设置响应头部,加一句代码:access-control-allow-origin:"*"或者允许交互的域名。
第三种,使用远程服务器nginx反向代理跨域
nginx就是一个高性能的服务器,还是一个反向代理服务器
步骤:
1.下载njinx,复制粘贴到远程桌面,(购买了远程桌面后,可以在浏览器连接登录,也可以在window自带的远程桌面连接)
2.将项目(dist),复制粘贴到njinx的根目录里面
3.在远程服务器中启动服务器
4.复制粘贴一段代码到远程服务器的记事本上
第四种:使用 (html5) 新增的,otherWindow.postMessage解决跨域, 是html5引入的API,postMessage()方法允许来自不同源的脚本采用异步方式进行有效的通信,可以实现跨文本文档,多窗口,跨域消息传递.多用于窗口间数据通信,这也使它成为跨域通信的一种有效的解决方案. ),但h5最大的问题就是兼容性,对ie无效
第五种:使用jQuery提供的jsonp
动态生成script标签,用src直接引入地址就可以了
vue实例从创建到销毁的过程,比如实例创建前后,模板渲染前后,数据更新前后,实例销毁前后一系列就是vue的生命周期
beforeCreate(){}: 组件创建 //组件开始初始化,仅仅注册组件自己的事件和生命周期函数 created(){}: 完成组件创建 //vue实例已经完成自定义data、methods、computed等属性初始化以及语法校验 beforeMount(){}: 挂载dom //vue实例仅仅是将el(template)属性指向的html编译成vue模板,此时并没有完成模板内容渲染 mounted(){}: 渲染dom //vue实例会将data数据渲染到编译的模板中并形成虚拟dom,替换el(template)指向dom beforeUpdata(){}: 更新数据 //vue实例中data数据发生改变,会触发该函数,但是页面中数据还是原始数据 updated(){}: 渲染dom //vue实例中data数据和页面中数据已经一致了 beforeDestroy(){}: //vue实例仅仅是开始销毁 data methods … destroyed(){}: // vue实例上的所有数 events child component(子组件) listener监听机制都将被销毁
vue的生命周期有八个钩子函数,可以在某些特定阶段自动执行某些功能
在vue生命周期的不同阶段通过对应的钩子函数来实现组件数据管理和DOM渲染两大重要功能。
mounted
路由是通过路径的不同来切换不同的页面
当我们在切换不同页面时,按理是需要重新发送请求的,而路由模式就将页面的状态保存到服务器,不需要再切换路由页面的时候,发送请求
路由的实现就是hash 和history
浏览器的History API可以使得页面跳转而不刷新,页面的状态就被维持在浏览器中了
在vue中路由模式使用 mode来进行指定
1.hash模式 默认模式 你不写就是hash模式
2.history模式
区别 | hash | history |
url展示上 | url带# | url不带# |
浏览器兼容性 | 兼容性好 | html5新特性所以对ie兼容性不好 |
浏览器刷新 | 刷新之后正常显示 | 上线之后刷新页面丢失 |
prams:三步走:在接受组件的路由规则的path后添加变量,
发送方:可以利用编程式或声明式:<router-link to="{name:'路由名字',prams:{变量名:数据}}"><>
接受方:this.$route.prams.变量名
query:两步走:和prams一样,少了第一步,而且发送方发送数据时既可以写路由的名字,也可以写path
将数据放到页面上:{{}}、v-text、v-html、v-bind插入数据属性值
全局组建可以再components里面写好一个vue的组件页面,然后在main.js中引入,然后使用Vue.component("全局组建的名字",引入组件的名字),记得在实例创建之前注册,当需要的使用的社会化,直接调用就行
创建一个新的vue实例,它承担起了同级组件之间的传值,这就成为中央事件总线
1.新建文件夹eventbus与文件用来存放这个中央事件总线的空实例
2.创建空实例
3.需要传递的组件中 引用中央事件总线 并且 使用事件来触发 给中央事件总线之上绑定一个自定义事件
4.在需要数据的组件之上 先引用中央事件总线 使用$on()来监听实例上的自定义事件
是用来监听实例上的自定义事件$emit( ),听取自定义事件包含的内容
也就是双向绑定的原理
双向绑定是通过 数据劫持 与 发布者订阅者模式来实现的
数据劫持:数据(变量)劫持(拦截)就是当数据改变的时候 我要拦截到这次改变 通知模型或者视图发生改变
通过一个Object.defineProperty()来监听数据当数据改变的时候他就会被触发 从而通知另外一方(有一个get的方法和set的方法 分别是读取与修改)
也有一个bug 后面会说先占个位置
bug详见$set
也就是当data数据发生改变时,视图不会改变,因为数据劫持只会拦截到data数据的初始化状态,后续在添加新的属性,视图是不会发生改变的,所以我们可以用$set方法,来给data添加新的属性
发布者订阅者模式:就是一个一对多的关系 ,当发布者改变了 其所有的订阅者页随之发生改变
双向绑定是通过 数据劫持 与 发布者订阅者模式来实现的
1,首先:将data中的数据对象进行遍历,给其属性都加上 setter 和 getter?
2,通过一个Object.defineProperty()来监听数据当数据改变的时候,就会触发setter
getter是使用数据的时候触发,setter是在修改数据的时候触发,触发setter也会触发watcher监听,从而通知DOM修改刷新(通过render函数进行渲染,生成真实的DOM)
observer:能够对数据对象的所有属性进行监听,如有变动可拿到最新值并通知订阅者(watcher)
watcher:作为连接observer(对象)和compile的桥梁,能够订阅并收到每个属性变动的通知,执行指令绑定的相应回调函数,从而更新视图
全局守卫,路由独享,组件内的局部守卫
全局守卫:所有配置路由的组件都会触发
全局前置:进入页面之前触发的函数
router.beforeEach((to,from,next)=>{
if(to.path=="/denglu"||to.path=="/zhuce"){
next()
} else {
alert("当前为付费页面请登录后访问!")
next("/denglu")
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。