目录标题
JavaScript
js简介
JavaScript(简称“JS”) 是一种具有函数优先的轻量级,解释型或即时编译型的编程语言。虽然它是作为开发Web页面的脚本语言而出名,但是它也被用到了很多非浏览器环境中,JavaScript 基于原型编程、多范式的动态脚本语言,并且支持面向对象、命令式、声明式、函数式编程范式。
JavaScript在1995年由Netscape公司的Brendan Eich,在网景导航者浏览器上首次设计实现而成。因为Netscape与Sun合作,Netscape管理层希望它外观看起来像Java,因此取名为JavaScript。但实际上它的语法风格与Self及Scheme较为接近。
JavaScript的标准是ECMAScript 。截至 2012 年,所有浏览器都完整的支持ECMAScript 5.1,旧版本的浏览器至少支持ECMAScript 3 标准。2015年6月17日,ECMA国际组织发布了ECMAScript的第六版,该版本正式名称为 ECMAScript 2015,但通常被称为ECMAScript 6 或者ES2015。
变量
变量就是存储数据的容器
变量是一个可以变化的量,数据可以发生变化
var
声明后不赋初始值 默认都为 undefined
可以同时声明多个变量并赋予初始值
var
变量可以重复定义
let
变量不能重复定义
const
常量
恒定不变的值为常量
声明时必须赋初始值 且声明后无法修改
获取元素
查询一个指定选择器的元素querySelector
查询所有指定选择器的元素querySelectorAll
通过id查询元素getElementById
通过类名查询元素getElementsByClassName
通过标签名查询元素getElementsByTagName
数据类型
undefined
未定义类型
一个变量声明后不赋值,则他的值为 undefined
未定义类型中只有一个值叫做 undefined
Boolean
布尔型数据
只有两个值 true 真 false 假
Number
数字类型
Infinity
代表无限大的数字
NaN
代表不是数
String
字符串类型
将很多的字符串起来就是字符串
可以使用单双引号来定义字符串
BigInt
长整型
用来描述一个位数非常长的整型数字
Symbol
符号
专用来创建类中的匿名属性或函数
null
空类型
空类型唯一的值就是 null
null 的含义: 用来代表对象类型的空引用(空指针)
Object
对象类型
对象是一组数据的集合
所有能被构造的(包含constructor构造器)类型都是对象
json
对象
json
(JavaScript Object Notation, JS 对象简谱) : 轻量化js数据结构
json 对象主要用于存储数据,有着简洁的数据结构,正由于这样的特点,json 对象常用于网络信息传输中,传递数据
运算符
三元运算符
用于判断一个表达式结果,为真时,返回结果1,为假时返回结果2
当嵌套三元运算符在同一行内书写,请给嵌套的三元运算符的表达式用圆括号包起来
console.log(obj.sex === 'male' ? '男': (obj.sex === 'female' ? '女' : '其他'));
比较运算符
比较运算符用于对运算符左右两个值进行比较
比较运算符的运算结果为boolean值,用于指示比较结果为真或者假
>
大于
<
小于
==
非严格相等判断
非严格相等判断 在运算符左右两边不需要使用相同的数据类型
当数据类型不同时 == 运算符将自动进行隐式转换
===
严格相等
类型和值都相等才会被认为相等
!=
非严格不等于
!==
严格不等于
算术运算符
+
加
-
减
*
乘
/
除
%
模运算
除以一个数字并取余
**
幂运算
运算 n 的 m 次方是多少
赋值运算符
+=
自增
等价于 a = a + 2
-=
自减
等价于 a = a - 5
*=
自乘
/=
自除
%=
自模
等价于 a = a % 3
++
自增
--
自减
逻辑运算符
符合逻辑条件时将返回真或假
&&
与
两个表达式都为真,结果返回真;任一一个表达式为假,结果返回假
||
或
两个表达式任一一个为真,结果返回真;否则为假
&&
和 ||
开发人员称为短路运算
短路运算的应用场景1:赋值默认值
!非
作用是取反
运算优先级顺序
++ --
> 算术运算符 > 比较运算符 > 逻辑运算符 === 三元运算符 > 赋值运算符
条件判断
switch条件判断
语法:判断value值为多少,如果为constant1则执行其后的代码
如果为constant2则执行其后的代码
如果不满足所有的case语句,则执行default
switch ( value ) {
case constant1:
break;
case constant2:
break;
... 可以有任意多个case语句
default: // default 不是必须要写的
break;
}
if条件判断
用于进行条件判断的语句
作用:当布尔表达式值为真时,执行后面的代码块
if(条件表达式) {
// code block 代码块
}
if else
如果…否则…
if(条件表达式) {
// code block 代码块
} else {
// code block
}
总结:
1.if 语句要么执行要么不执行
2. if else 语句,一定有一个会被执行,二选一
3. if else if 语句,多选一或都不执行
4. if else if else 语句,一定有一个会被执行,多选一
循环
循环就是重复执行某一段代码的行为
for
循环
例如按次数进行循环
语法:
for( 初始化语句; 循环条件; code block 运行一次结束后运行的代码 )
初始化语句:初始化变量值
循环条件:循环条件是个布尔表达式,若结果为真,则执行 code block 的代码块
let count = 5 // 循环次数
for (let i = 0; i < count; i++) {
//code block
}
数组
存储一组数据的一个容器
声明数组
let arr = []
数组的操作:
push
追加数据到数组末尾
pop
从尾部取出一个成员
unshift
在头部添加数据
shift
从头部取出一个成员
push 和 unshift 可以批量添加成员
splice
删除指定位置的成员,并用新成员替换,或插入新成员到指定成员的前面
第一个参数:删除成员的起始位置
第二个参数:删除成员的个数
第三个参数:用于替换被删除成员的新数据,该参数可以省略
concat
连接数组
join
使数组成员用一个字符连接起来
includes
判断是否包含某成员
indexOf
查询指定数组成员的索引
lastIndexOf
查询最后一个指定数组成员的索引
slice
数组切片 获取子数组
函数
站在开发人员的角度讲:函数是对一段程序的封装(封装:包装)
站在生活的角度来讲:函数就是帮我们完成某样任务的机器
语法:
function 函数名(参数列表) {
// code block 代码块
}
内存堆栈
调用函数时,函数中的各种变量将存储在内存中,以堆栈的形式进行保存
堆
用于存储对象数据的内存区域
栈
指的是一种先进后出的数据格式 用于存储每次函数调用时产生的数据
栈
中的每一次调用内容,称为一个栈帧
总结:
栈将在调用函数时创建数据并进入栈,这个过程称为入栈
函数调用结束后将函数中的数据将从栈中移除,这个过程称为出栈
出栈时候,释放内存中已经无用的数据的过程称为垃圾回收
函数调用时栈的存放顺序始终是先进后出
lambda表达式
lambda 表达式是一种用来定义函数的方法
lambda 表达式也称为箭头函数
圆括号部分是参数列表
花括号部分是代码块
const sayHello = () => {
console.log('hello');
}
bind、call、apply
bind
绑定函数的 this 指代
语法 function.bind(thisArg, x, y, …)
thisArg: 要修改的this的指代
x, y, … : 函数的参数,选填
返回值: 一个被修改了this指代后的新函数
call
调用函数并指定 this 指代
语法: function.call(thisArg, x, y, …)
thisArg: 要修改的this的指代
x, y, … : 函数的参数,选填
返回值: 函数本身的返回值
apply
调用函数并指定 this 指代
语法: function.apply(thisArg, [x, y, …])
thisArg: 要修改的this的指代
x, y, … : 函数的参数,选填
返回值: 函数本身的返回值
变量的作用域
作用域指的是作用范围,范围内可以访问变量,超出范围则无法访问
作用域一共只有三种:
Global
全局作用域
Block
块级作用域
Function
函数作用域
全局作用域(Global
)
具备全局作用域的只有全局变量或常量
全局变量指的是作用域为全局(Global)的变量,代码中任何位置都能使用
全局变量有两种
1.自动全局变量
给未定义的变量直接赋值,该变量会变成 自动全局变量,若在浏览器中,该变量会被存到window对象里
2. (普通的)全局变量
直接在函数外声明的变量也是全局作用域的变量
块级作用域(Block
)
块级作用域就是在代码块中有效的作用域
if (true) {
let a = 1
console.log(a);
}
函数作用域(Function
)
函数中的变量,无论使用var还是let定义的,都是函数作用域,在函数外无法访问
总结:
函数外声明的变量 作用域是全局
函数内用关键字声明的变量 作用域是函数内
let 声明的变量具备块级作用域
字符串操作
str.length
查看字符串长度
str[4]
通过索引访问字符串中的字符
charAt
函数可以获取指定索引处的字符
split
分割字符串
trim
去掉字符串首尾空格
substring
截取子字符串
第一个参数:截取字符串的起始索引位置
第二个参数:截取字符串的结束索引位置
indexOf
查询字符串中指定字符在字符串中的索引位置
startsWith
用于判断字符串是否以指定字符串开头
toUpperCase
toLowerCase
将字符串中的英文转成全为大写或小写
正则表达式
用于匹配字符串的表达式
可以写一个正则表达式,用于鉴定一个字符串是否是邮箱格式的字符串
\
斜杠:转义
^
匹配字符串的开头
$
匹配字符串的结尾
*
匹配任意次
?
匹配0次或1次
+
匹配至少1次
{n}
匹配指定次数
{n,}
匹配至少n次
{n,m}
匹配至少n次,至多m次
[xyz]
匹配字符集合,匹配一个字符,该字符在方括号内
x|y
匹配x或y
[^xyz]
匹配负值集合,匹配一个字符,该字符不在方括号内
[a-z]
[0-9]
取范围值,匹配一个字符,该字符在指定范围内
[^5-7]
取范围负值,匹配一个字符,该字符不在指定范围内
(pattern)
将pattern里面的所有字符当作一个字符处理
特殊字符:
\d
10进制数
\D
非10进制数
\r
回车
\n
换行
\s
所有不可见字符,制表符 回车换行 空格等
\S
所有可见字符
.
基本等于任意字符 但不包括 \r\n
\t
制表符
匹配任意字符任意次数的写法如下:
regex = /[\S\s]*/
全局模式
不开全局模式 只会匹配到第一个符合条件的字符串
全局模式的正则表达式将匹配所有符合条件的字符串
在正则表达式的后面使用 g flag 来开启全局模式
matchAll
匹配所有符合正则描述的字符串
参数必须是一个全局模式的正则表达式
贪婪模式:字符串在匹配正则表达式时,将尽可能多的匹配满足正则规则的字符
非贪婪模式:字符串在匹配正则表达式时,将尽可能少的匹配满足正则规则的字符
默认情况字符串将执行贪婪模式的匹配
在表示匹配个数的符号后面加上’?'问号开启非贪婪模式
计时器
当经过指定时间后触发一段代码的函数就是一个计时器
setTimeout
声明一个计时器
第一个参数:计时器计时结束后触发的函数
第二个参数:计时时长,单位:毫秒
let timerId = setTimeout(() => {
console.log('hello setTimeout')
}, 3000)
clearTimeout
清空计时器
setInterval 循环计时函数
每次经过指定时间,触发一次指定的函数
let count = 0
let timerId2 = setInterval(() => {
count++
console.log(count);
}, 1000)
移动
使用计时器 每隔一段时间 让元素位置产生一个增量的变化
//获取元素
const box = document.querySelector('.box')
let timerId = setInterval(() => {
// 一个动画帧
// 先运行逻辑运算
// 设一个速度,一帧移动15像素
let v = 15
// 当前的距离值
let distance = getComputedStyle(box).left
distance = Number(distance.substring(0, distance.length - 2))
// 叠加速度后的距离
distance += v
if (distance >= 500) {
// 停止计时器
clearInterval(timerId)
}
// 再渲染到元素上
box.style.left = `${distance}px`
}, 200)
时间对象
时间对象 Date
创建时间对象的方法
语法:new Date(params)
当前系统时间
let date = new Date()
创建指定时间字符串的时间
date = new Date('1997-07-07')
通过格林威治毫秒时创建时间
date = new Date(1000 * 60 * 60 * 24 * 365)
通过年月日时分秒创建时间
date = new Date(2000, 5, 6, 18, 44, 22)
date.getFullYear
年
date.getMonth
月
date.getDate
日
date.getHour
时
date.getMinutes
分
date.getSeconds
秒
date.getMilliseconds
毫秒
数学函数
专门用于处理数学运算的函数
数学函数可以通过浏览器内置对象Math进行直接调用
abs
获取数字的绝对值
console.log(Math.abs(-100));
console.log(Math.abs(100));
ceil
一个小数向上取整
console.log(Math.ceil(5.1));
console.log(Math.ceil(5.9));
floor
一个小数向下取整
console.log(Math.floor(5.1));
console.log(Math.floor(5.9));
round
四舍五入
console.log(Math.round(5.1));
console.log(Math.round(5.9));
max
取参数中较大数
console.log(Math.max(1, 2, 3, 4, 5, 6, 7));
min
取参数中较小数
console.log(Math.min(1, 2, 3, 4, 5, 6, 7));
pow
返回x的y次方
console.log(Math.pow(2, 3));
sqrt
返回一个数的平方根
console.log(Math.sqrt(25));
random
取随机数,范围在[0~1)之间,能取到0但取不到1
console.log(Math.random());
sign
取符号
console.log(Math.sign(-32))
console.log(Math.sign(80))
事件函数
事件就是某种事情
在js中,事件就是:当某种情况发生的时候,能够触发一段代码,这个发生的情况就是事件
将自定义的函数和某个事件进行捆绑,绑定后的效果就是:(当。。。时,发生的时候,就会触发我们绑定的函数)
addEventListener
绑定事件
第一个参数:要绑定的事件名称
第二个参数:当事件发生时,触发的函数
第二个参数的函数,不是有开发人员调用的,当事件发生时由浏览器调用的
const btn1 = document.querySelector('.btn1')
// 声明一个事件处理程序
function btn1Clicked(event) {
// event 是触发的事件对象
console.log(event);
// this 关键字代表被添加该事件处理程序的dom对象
console.log(this);
}
// 给btn1添加事件监听器
btn1.addEventListener('click', btn1Clicked)
解绑事件
// 解绑事件
const btn2 = document.querySelector('.btn2')
btn2.addEventListener('click', () => {
// 移出事件监听器
// 调用removeEventListener来解绑事件
// 参数一:要解绑的事件名称
// 参数二:要解绑的事件处理程序
btn1.removeEventListener('click', btn1Clicked)
})
事件分类
格式:
box2.addEventListener('参数', () => {
console.log('');
})
load
加载完成
error
加载失败
focus
获取焦点
blur
失去焦点
click
点击事件
contextmenu
右键菜单
dblclick
双击事件
mousedown
鼠标点下
ev.button
用于区分点击的是哪个键
0: 左键 1: 中键 2: 右键
mouseup
鼠标抬起
mouseenter
进入事件
mouseleave
离开事件
mousemove
移动事件
offsetX
offsetY
是鼠标相对于元素左上角的坐标
wheel
滚轮事件
deltaY
纵向滚动的变化量
正数向下 负数向上
drag
拖动事件
元素上需要添加 draggable="true"
dragstart
开始拖动
dragend
结束拖动
change
变化事件
keydown
按下
可以按住不放持续触发事件
keyup
抬起
keypress
按压
屏蔽默认事件
方法一: 使用事件对象屏蔽元素事件的默认行为
ev.preventDefault()
屏蔽当前元素默认的事件行为
方法二: 对应事件属性 retrun false
也能屏蔽默认行为
冒泡
在html中触发事件的元素,将会把事件不断的向父元素传递,这个过程叫做事件冒泡
document.querySelector('button').addEventListener('click', () => {
//阻止事件冒泡
ev.stopPropagation()
console.log('button');
})
document.querySelector('div').addEventListener('click', () => {
console.log('div');
})
document.body.addEventListener('click', () => {
console.log('body');
})
可以使用事件对象的 stopPropagation 来阻止事件冒泡
捕获事件
事件触发后,可以由上级元素先处理事件,这个过程就是捕获事件
true
代表要捕获事件的元素
document.querySelector('button').addEventListener('click', () => {
console.log('button');
})
document.querySelector('div').addEventListener('click', () => {
console.log('div');
})
// addEventListener 的第三个参数代表是否捕获事件
// 捕获事件的元素会先处理事件,然后将事件对象还给产生事件的元素,然后正常冒泡
document.body.addEventListener('click', () => {
console.log('body');
}, true)
面向对象编程
面向过程编程:根据功能逻辑,按照功能和代码的执行顺序编写代码,且以计算机的运行逻辑按照1234的步骤书写的代码,这就是面向过程的编程方法
面向对象编程(OOP:Object Oriented Programming):站在现实生活的角度,将计算机中的抽象的物体当作一个具体的东西(这个东西就叫做对象Object)来处理,这就是面向对象编程的思想
json
对象
json 对象是js中的对象,且该对象的格式采用json的格式(js中也称为朴素对象 plain object)
json是一种js的轻量化交互式数据
什么是对象,js用属性和行为来描述某个物体而产生的一种数据结构,该数据称为对象
设计一个对象最重要的就是设计它的属性和行为
属性: 都是一些值
行为: 都是一些函数
let duck = {
// 设计对象属性如下
color: '#0f0',
age: 2,
name: '鸭宝',
// 对象行为
// 对象的行为一般称为方法
swim() {
console.log(`鸭子在游泳`);
},
shout() {
console.log('叫啦');
},
fly() {
console.log('鸭在飞');
}
}
调用对象属性和行为
console.log(duck.name);
duck.fly()
class
类
用于描述同类事物的类型叫做类,类型是抽象的
构造函数: 用于构造类实例的函数
function Human(name, age, sex){
// 在类型中 this 关键字 代表当前实例对象
// 属性
this.name = name
this.age = age
this.sex = sex
// 行为
this.eat = function(food){
// 方法中使用this访问实例对象
console.log(`${this.name} 正在吃 ${food}`);
}
}
静态属性和方法
静态属性和方法 指的就是一类中共有的属性和方法
class 类中 用static
关键字声明静态属性和方法
静态属性是属于类的属性
用来描述这个类
静态方法,用来描述一个类的行为
调用静态属性或方法,使用类名调用而不是实例对象
私有属性和方法
在实例对象内能使用但是实例对象外无法使用的属性和方法,称为私有属性和方法
私有方法或属性在名称的前面使用 # 井号
#engine = '这是发动机'
this
根据不同的场景,this关键字代表东西不同
js 执行上下文中的 this 指向的是window
函数内的this 指向的是window
json对象方法的this 指向的是对象自己
实例对象方法的this 指向的是调用该方法的实例对象
对象方法中的this始终是自己
总结:
1.js 执行上下文 => window
2.函数内 this => window (函数=>window)
3.方法内的this指向调用方法的对象 (方法=>实例)
4.this 可能被其他函数赋值 例如 addEventListener 这种时候 this 既不是 window 也不是 undefined,它取决于函数 addEventListener 自己
严格模式
为了代码更规范,避免一些错误与 js
历史问题所产生的歧义
严格模式中不准做的事情
未声明变量就直接赋值
直接删除变量
重复定义参数名
不允许使用 8 进制数
不允许使用八进制转义字符
不允许赋值只读属性
删除不允许删除的属性
不能使用 with
语法
不能用 eval()
函数创建变量
开启严格模式的方法
在 script 标签或 js 文件的顶部,在函数内的第一行,均可以输入 'use strict'
来开启严格模式
继承
从父类传承下他的属性和行为,使子类具备相同的属性和行为,同时子类可以拥有自己的属性和行为
父类(parent class)也叫做基类(base class),也叫超类(super class)
class 类 语法下的继承
class Human {
name
sex
sleep() {
console.log('人类在睡觉');
}
}
使用 extends 关键继承父类
class Eurapean extends Human {
// 子类可以有自己的属性和行为
luck = true
detox() {
console.log(`远离黄赌毒 珍爱生命`);
}
// 子类可以拥有和父类相同的方法,用来覆盖父类的方法
// 这种方法称为 方法的重写 (override)
sleep() {
console.log(`${this.name} 在睡觉`);
}
}