ES简介:
ECMAScript是一种由Ecma国际(前身为欧洲计算机制造商协会,英文名称是European Computer Manufacturers Association)通过ECMA-262标准化的脚本程序设计语言。这种语言在万维网上应用广泛,它往往被称为JavaScript或JScript,但实际上后两者是ECMA-262标准的实现和扩展。
ECMAScript 规范定义了一种脚本语言实现应该包含的内容,但是,因为它是可扩充的,所以其实现所提供的功能与这个最小集相比可能变化很大。 ECMAScript本身并不是一种脚本语言。正如在 Web 应用程序中执行有用操作的 bean 集合(例如,Netscape 的 AWT)是 Sun 的 JavaBean 规范的一种实现一样,JavaScript 是 ECMAScript 规范的一种实现。
目前使用最广泛的是ES5和ES6.
JS声明变量和常量
-
ES5:
var--- var可以重复声明格式:
var 标识符; var arr = []; var num1 = 1; var num2 = 12.34; var bool = true; var obj = {}; -
ES6:
let(声明变量)`const`(声明常量,必须初始化)--- 不可以重复声明(let 与 var、let 与 const、const 与 var)格式:
let 标识符; const 常量名 = 值; let i = 1; i = 1.23; console.log(i) const PI = 3.14; console.log(PI);
两个版本关键字的区别
-
ES5关键字var可以重复声明变量,
-
ES6关键字let/const ,不能重复声明,并且由于js中的预处理机制会直接报错,不会输出有任何结果
预处理: 预处理是因为js会首先把全盘的js扫描一遍,所以就产生了预处理。——暂时性死区
扩展知识
变量声明提前
-
如果给一个未声明的变量赋值,则JS会使用var关键字
F82 = 123; console.log(F82); //123 var F82 = "ABC"; console.log(F82); //ABC -
局部作用域中除函数外var声明的变量会提升为全局变量(只提升变量的声明,提升到全局第一行)----------------------->就可以先使用后声明
onsole.log(advance);//undefined { var advance = 'advance'; } -
执行到给未声明变量赋值的语句才会补关键字var
console.log(rr); var rr = 123;//undefined rr = 123;//rr is not defined
作用域
作用域指一个变量的作用的范围
全局作用域
-
直接编写在script标签中的JS代码,都在全局作用域
-
全局作用域在页面打开时创建,在页面关闭时销毁
-
在全局作用域中有一个全局对象window,他代表的是一个浏览器的窗口,它由浏览器创建,我们可以直接使用
-
在全部作用域中:
创建的变量都会作为window对象的属性保存
创建的函数都会作为window对象的方法保存
-
全局作用域中的变量都是全局变量,在页面的任意部分都可以访问得到
函数作用域(局部作用域)
1. 用函数时创建函数的作用域,函数执行完毕以后,函数作用域销毁
2. 每调用一次函数就会新建一个新的函数作用域,他们之间是相互独立的
3. 在函数作用域中可以访问到全局作用域的变量,在全局作用域中无法访问到函数作用域的变量
4. 当在函数作用域操作一个变量时,它会先在自身作用域中寻找,如果有就直接使用
如果没有则向上一级作用域中寻找,直到找到全局作用域
如果全局作用域中依然没找到,则会报错ReferenceError
5. 在函数中要访问全局变量可以使用Windows对象
在函数作用域中也有声明提前的特性,使用var关键字声明的变量,会在函数中所有的代码执行之前被声明,函数声明也会在函数中所有的代码执行前执行
函数的声明提前量
使用函数声明形式创建的函数function 函数(){},会在所有代码之前创建,所以可以在函数声明前调用函数
使用函数表达式和构造函数创建的函数,不会被声明提前,所以不能在声明前调用
JS 数据类型
判断表示(变量)类型
书写格式:
typeof 标识符
基本数据类型(简单)
String
表示:
//双引号嵌套
let str1 = "hello";
//单引号嵌套
let str2 = 'world';
let year = 2022;
//模板字符串
let str2 = `hello ${str2},今年是${year}年`;//hello world,今年是2022年
注:模板字符串
书写格式:内容前后加“`”
特征:1. 识别变量 书写:${变量名};2. 换行不会报错,并按照代码书写格式输出。
转义字符
\n 、 \t、 \r、 \b、 \f、 \v、 \\、\'、 \"
Number
取值
- 整型
- 浮点数
- NaN (is not a number)
let age = 18;
判断数据是不是NaN
书写格式:isNaN(判断的内容) -->true表示非数字,false表示纯数字,通常与取反配合
let inputNum = "123" - 0;
console.log(isNaN(inputNum)); //false
if (!isNaN(inputNum)) {
//需求:纯数字才执行业务逻辑
}
Boolean
取值
- true
- false
以下内容作为判断条件时,会隐式转换为false
- 空字符串 -->''、""、``
- 0
- fasle
- undefined
- null
- NaN
if (NaN) {
console.log(true);
} else {
console.log(false);
}//fasle
Undefined
取值
undefined
- 变量声明未赋值
- 赋值为undefined
- 获取未声明变量的类型(即不会报错)
- 读取超出数组长度下标的数据值
- 执行到函数的最后,如果没有return,那么返回值就是undefined
- 访问对象不存在的属性或方法
重点:
未初始化的变量
变量未声明(获取未声明变量的类型) 或 变量声明未赋值 或者 函数形参未赋值
赋值为undefined
访问不存在的对象属性或方法
越界索引数组元素
不返回任何结果的函数的调用结果(函数return没有值 、函数没有return)
let F82;
console.log(F82); //undefined
console.log(typeof F90);//undefined
Null
取值
null
let test = null;
console.log(test); //null
console.log(typeof test); //object
Symbol
基本数据类型之间的转换
强制转换(String、Boolean、Number)
书写格式:
类型(转换的变量)
//String -- > Number
let str1 = "hello123";
let str2 = "123";
let num1 = Number(str1);//NaN(number)
let num2 = Number(str2);//123(number)
//String -- >Boolean
let str3 = "";
let bol1 = Boolean(str1);//true
let bol2 = Boolean(str3);//false
//Number -- > String
let str4 = String(num1);//NaN(string)
let str5 = String(num2);//123(string)
//Number -- > Boolean
let num3 = 1;
let num4 = 0;
let bol3 = Boolean(num3);//true
let bol4 = Boolean(num4);//false
//Boolean -- > String
let str6 = String(bol3);//ture(string)
//Boolean -- >Number
let num5 = Number(bol3);//1
let num6 = Number(bol4);//0
隐式转换
let num = '123' - 0;
console.log(num,typeof num);//123,number
let str = num + "";
console.log(str,typeof str);//123,string
let bol1 = !!123;
console.log(bol1);true
扩展
-
在字符串前面加正号或负号,则隐式转换为number
-
提炼字符串中的数字:判断第一位是不是数值,如果是从第一位开始提,一直到不是数值的前一位。注:如果第一位就不是数值,则返回NaN
parseInt()
let num = "123abc"; let result = parseInt(num);//123 num = "-123abc"; result = parseInt(num);-123parseFloat()
let num5 = "123.43sf"; result = parseFloat(num5);//123.43
引用数据类型(复杂)
Object
运算符
一元运算符
自增 ++
前缀加
++i :先加再用
后缀加
i++ :先用再加
自减 --
前缀减
--i:先减再用
后缀减
i--:先用再减
算术运算符
+、- 、*、/、%
其中+运算符在运算的时候一侧有字符串,则会做字符串拼接。
赋值运算符
=、+=、-=、*=、/=、%=
逻辑运算符
- 或 || 规则:一真全真(短路运算符)
- 与 && 规则:一假全假(短路运算符)
- 非 !
非布尔值进行与或计算时,会将其转换成布尔值在再运算,并且返回原值
result = (1+2)|| "B" ||"C";//3 短路,返回第一个为真的,全是假的则返回最后一个
result = (1+2)&& true &&"F";//F 短路,返回第一个为假的,全是真的则返回最后一个
位运算符
- 按位或 |
- 按位与 &
- 按位非 ~
console.log(1 | 2); //3
console.log(1 & 2); //0
console.log(3 & 3); //3
比较运算符
返回值:Boolean
在一侧有数字比较的时候会被隐式转换成Number
console.log(1 > 2); //false
console.log(1 < 2); //true
console.log(1 == 2); //false
console.log(1 != 2); //true
console.log(1 >= 2); //false
console.log(1 <= 2); //true
console.log(1 == "1"); //true --- "1"转数值
console.log(1 === "1"); //false
console.log(1 === 1); //true
//NaN不等于任何值,包括他自己。
result = "123" - 2;
console.log(result == NaN); //false
console.log(null == NaN); //false
console.log(undefined == NaN); //false
console.log(false == NaN); //false
console.log(NaN == NaN); //false
console.log(NaN === NaN); //false
console.log(1 == true); //true
console.log("1a2" > "1c2"); //false
三目运算符
书写格式: 表达式1?表达式2:表达式3
适用条件:简单的判断+简单的执行语句
如果表达式1为true则执行表达式2,为假则执行表达式3
result = 1 > 2 ? true : false;
console.log(result); //false
运算符优先级
【运算符优先级】 从高到低
1、. [] () 2、++ -- - ! typeof ~ new delete void 3、* / % 4、+ - + 5、> >= < <= instaceof 6、== != === !== 7、&& 8、|| 9、? :三目运算符 10、= 赋值 11、 , 多重赋值
条件分支语句
单分支语句
书写格式:if(条件){代码块}
功能:如果满足条件则执行大括号代码块
双分支语句
书写格式: if(条件){代码块} else{代码块}
功能:如果满足条件则执行if大括号里的代码块; 反之,执行else大括号里的代码块
多分支语句
书写格式:
if(条件1){代码块1}
else if(条件2){代码块2}
...
else if(条件n){代码块n}
else {代码块n+1}
功能:满足条件1,则执行代码块1
不满足条件1,则执行else后条件2的if语句。
依次类推,执行满足条件的代码块。
如果所有条件都不满足,则执行最后一个else后没有if的else的代码块
注: 如果所有else后面都有if,并且所有条件都不满足,则不执行任何代码块
switch语句
书写格式:
switch (匹配值) {
case 表达式1:
{ 代码块1 }
case 表达式2:
{ 代码块2 }
}
功能:匹配值与表达式1全等时,执行相应case后的代码块,并且会继续执行全等case后case的代码
为了只执行全等case后的代码,则所有case后的代码块,都添加关键字break;
循环语句
循环是由反复被执行的 循环体语句 和 循环终止的条件 共同组成的。
while 当循环
格式:
while(条件){
循环代码
}
-
如果条件为true,则执行循环代码,否则不执行
-
不知道明确循环次数,先验循环
do while循环
格式:
do{
循环的代码
}while(条件);
- 首先执行循环体的内容,然后根据条件的真假是否继续循环
do-while循环是后验循环,即先执行再判断,至少判断一次
for循环
格式:
for(表达式1;表达式2;表达式3){
循环体语句
}
- for 里的表达式可以不写,但必须有
;; - 表达式1-------声明一个循环控制变量,记录循环开始的起始值 标准写法:
let i = 0;;表达式2-------是一个布尔表达式,用来判定什么时候继续循环,当它为true时,就会继续循环, 当它为false时,就会退出for循环结束},继续向下执行;表达式3------- 用来控制循环控制变量的自改变的,又被称为步长i++; - for循环中的语句执行的顺序:
- .一旦遇到for循环,首先执行表达式1;
- 然后马上判断表达式2,如果为
true进入循环体;为false,退出循环 - 循环体执行完以后,执行表达式3;
- 然后回到步骤2;
循环中断
break
跳出本层循环体和switch语句,从而提前结束switch和本层循环(离它最近的循环)
continue
终止本次循环continue后的代码,执行下一次循环(while和do while是进入下一次判断,而for是执行语句3)
扩展
终止循环
- 创建书写格式:自定义名称 冒号 循环
- 使用书写格式:break 自定义名称 分号
F110:for (let i = 1; i < 3; i++) {
for (let j = 0; j <= 3; j++) {
console.log(i, j);
if (j > 0) {
break F110;
}
}
}
//跳出指定循环,兼容性差
断点
调试,监控数据
数组
数组的功能是存储数据,与变量的区别是其可以一个标识符存储多个数据。js的数组可以存储任意形式的数据。数组是引用数据类型。
堆、栈
- 栈存储的是基本数据类型和引用数据类型的地址
- 堆存储的是引用数据类型的数据
注:基本数据类型之间是值的比较,引用数据类型之间是地址的比较(本质上都是栈中存的 值比较),所有内存开辟都是在栈里面的,所以基本数据类型的值是相等的,引用数据类型的地址是不相等的。
创建数组方式(声明形式)
字面量方式
关键字 数组名 赋值符号 中括号 分号
let arr = [1, 2, 3, 4, 5];
let arr = [];
console.log(typeof arr);//object
构造函数方式
关键字 数组名 赋值符号 new Array() 分号
let arr1 = new Array();
获取数组中的数据
- 数组名[下标],下标起始值是0
- 获取数组存储数据的个数
数组名.length
let arr4 = [1, "a", true, undefined, null, NaN];
console.log(arr4);//[1, "a", true, undefined, null, NaN]
//获取数组存储数据的个数
console.log(arr4.length);
//获取超出数组长度的数据为undefined
console.log(arr4[10]);//undefined——>为了防治报错,添加一个数据,数组数据默认值都是undefined
//不会改变数组的存储数据
console.log(arr4.length);//6——>为了防治报错,看了就删
数组赋值
- 初始化时赋值
array[index] = value;,该下标有值时为修改数据,无值时则是添加数据
arr4[arr4.length] = "hello";
//存储数据的下标超出数组长度
//从存储的下标到数组长度之间的内容为empty
arr4[11] = "world";
console.log(arr4);//[1, "a", true, undefined, null, NaN, "hello", <4 empty items>",world"]
操作数组
增加数据
- 给未赋值下标进行赋值
- 通过数组的方法
push(),在数组的末尾批量添加数据,中间使用","隔开,返回值是添加成功后的数组长度unshift(),在数组的开头批量添加数据,中间使用","隔开,返回值是添加成功后的数组长度
let array1 = ["a", "b", "c", "d"];
array1.push(1, 1, 2);
console.log(array1);//["a","b","c","d",1,1,2]
let temp = array1.unshift("aa", "s", 'ss');
console.log(array1,temp);//10
删除数据
通过数组的方法:
pop(),无参方法,删除数组最后一个数据,返回值是被删除的数据shift(),无参方法,删除数组第一个数据,返回值是被删除的数据
let tmp = array1.pop();//删除最后一个数据
console.log(array1,tmp)
tmp = array1.shift();//删除第一个数据
console.log(array1,tmp)
-
清空数组
1. 循环——>pop,shift2.
arr = [];3.arr.length = 0;
修改+插入
-
给有值下标进行赋值
-
splice(),数组的splice()方法,返回被删除内容的数组,会改变原数组
- 取一个参数:以该参数为起始下标,一直删除到数组最后一个值
- 取两个参数:第一个参——>起始下标,第二个参——>删除的个数
- 取三个(及以上)参数:第一个参——>起始下标,第二个参——>删除的个数,第三个参及以后的——>替换或插入的数据【第二个参数为0则是插入,否则为替换】
console.log(array1);//["s","ss","a","b","c","d",1,1]
array1.splice(3);//删除下标为3以及之后的数据
array1.splice(0, 2);//删除下标0开始的2个数据
//替换数据
array1.splice(1, 0, "a", "b", "c");//在下标1开始添加多个数据(纯添加)
剪切
slice方法:获取数组中的数据,返回一个新数组,包含从开始下标到结束下标的数据 (不包含结束下标)
- 取1个参数:获取数组从参数为起始位置到数组最后一个数据的内容
- 取2个参数:参数1为起始位置,参数2为结束位置。获取数组从参数为起始位置到第二个参数为结束位置(不含参数2为下标)的数据
注:
- 不改变原数组
- 参数为负数时,则结果为数组长度与其相加
反转数组
数组名.reverse():把数组中的数据进行反转,将改变原始数组
查询数组中的数据
-
数组名.includes(查找的值),返回布尔值 -
数组名.indexOf(查找的值),找到返回下标,如果没有找到返回-1 注:从前往后找,匹配第一个满足条件的值,就不会再查找了
-
数组名.lastIndexOf(查找的值),找到返回下标,如果没有找到返回-1注:从后往前找,匹配第一个满足条件的值,就不会再查找了
数组中数据进行排序
数组名.sort(),把数组中的数据排序,返回排序后的数组。(需要函数修正)
注:sort() 方法会改变原始数组
//return a-b 升序
//return b-a 降序
let array4 = ["A", "B", "C", "D", "E", "F", "G", "H", "I", "J"];
array4.sort(function (a, b) {
return a - b;//升序
}
);
console.log(array4);//["A","B","C","D","E","F","G","H","I","J"]
合并数组
concat
arr1.concat(arr2);//返回一个新数组
二维数组转一维数组
arr.flat();
字符串与数组之间的转换
字符串转数组
字符串.split(分隔符)- 功能:以分隔符来划分字符串的数据个数
- 返回值:数组
注意:
- 无参则把字符串整体作为一个数据存储到数组中
- 参数是空串,则把字符串每一位作为一个数据存储到数组中
let str ="2022-6-7";
let arr = str.split("-");//["2022","6","7"]
数组转字符串
数组名.join(分隔符)- 功能:以参数作为数组中每个数据之间的分隔符,拼成一个字符串
- 返回值:字符串
注意:
- 无参则把数组整体作为一个字符串返回
- 参数是空串,则把数组每一位作为一个字符串返回
let arr = str.split("-");//["2022","6","7"]
str = arr.join("/");//"2022/6/7"
扩展运算符
在数组和字符串的运用中是扩展的作用,在函数不定参数的运用中是起整合的作用。
...
字符串转数组
str = "hello";//把字符串按位拆开
arr = [...str];//["h","e","l","l","o"],拆开后放到数组中
合并多个数组
let arr1 = [1,2,3];
let arr2 = [4,5,6];
let arr3 = [...arr1,...arr2];//[1,2,3,4,5,6],把多个数组合并成一个数组
求数组数值的最值
let arr3 = [...arr1,...arr2];//[1,2,3,4,5,6]
console.log(Math.max(...arr3));//6
数组去重
//数组去重
//法1:
let array = [1, 2, 3, 3, 3, 4, 5, 6, 4, 4, 4, 2, 3, 4, 2, 1, 1, 3, 1];
for (let i = 0; i < array.length; i++) {
for (let j = i + 1; j < array.length; j++) {
if (array[i] === array[j]) {
array.splice(j, 1);//删除数组中的元素
j--;//因为删除了一个元素,所以j要减1
}
}
}
console.log(array);
//法2:
let array2 = [1, 2, 3, 3, 3, 4, 5, 6, 4, 4, 4, 2, 3, 4, 2, 1, 1, 3, 1];
for (let index = 0; index < array2.length; index++) {
if (!(array2.indexOf(array2[index]) === array2.lastIndexOf(array2[index]))) {
array2.splice(array2.lastIndexOf(array2[index]), 1);
index--;//只要重复就要反复判断,避免漏判
}
}
console.log(array2);
//法3:
let array3 = [1, 2, 3, 3, 3, 4, 5, 6, 4, 4, 4, 2, 3, 4, 2, 1, 1, 3, 1];
let array4 = [];
for (let index = 0; index < array3.length; index++) {
if (array4.indexOf(array3[index]) === -1) {
array4.push(array3[index]);
}
}
array3 = array4;
console.log(array3);
数组的遍历
循环
- 普通for循环
- for of循环,遍历键值
- for in循环,遍历键名
let arr = [1,2,3,4,5,6,7,8,9,10];
for(let key in arr){
console.log(key);//0,1,2,3,4,5,6,7,8,9————>遍历键名
}
for(let key of arr){
console.log(key);//1,2,3,4,5,6,7,8,9,10————>遍历键值
}
方法
- map()方法,遍历数组,返回值是一个新数组
- forEach()方法,遍历数组,没有返回值
- filter()方法,遍历数组,返回值是一个新数组
- reduce()方法,遍历数组,返回值是一个值
- reduceRight()方法,遍历数组,返回值是一个新数组
集合
数据结构--集合,ES6新增了Set数据结构。 Set数据结构本质上是一个数组,但是他的成员的值都是唯一的,没有重复的值。存储的数据具有唯一性(全等)。
声明集合
书写格式:关键字 集合名 赋值符号 new Set() 分号
let set = new Set();
console.log(typeof set);//object
集合的初始化
let set = new Set([1,2,4,6]);
集合的赋值
书写格式:集合名.add(值),添加一个值,返回的是添加成功后的集合本身
set.add(1);
set.add(true);
let temp = set.add(2);
let temp1 = set.add(true);//添加重复的值,不会添加
console.log(temp,temp1);
console.log(set);
删除数据
书写格式:集合名.delete(值),删除一个值
返回值:删除成功返回true,删除失败返回false
let temp2 = set.delete(1);//删除成功返回true,失败返回false
console.log(set,temp2);//Set { true, 2 } true
集合属性
size
书写格式:集合名.size,获取集合的长度
console.log(set.size);
清空集合
书写格式:集合名.clear()
set.clear();
查找数据
书写格式:集合名.has(查找内容),查找一个值是否存在,存在返回true,不存在返回false
console.log(set.has(1));//true
数组去重
数组转集合,集合再转数组,就可以达到数组去重的效果。
let arr = [1,2,3,4,3,2,4];
let set1 = new Set(arr);//数组转集合
console.log(set1);//Set(4) {1, 2, 3, 4}
arr = [...set1];//集合转数组
console.log(arr);//[1, 2, 3, 4]
【扩展——链式调用】
set.add("a").add("b").add("c");因为返回的是自己本身,所以可以链式调用
Array.splice(1,2).join("").splice(1,2).join("");
let str = "abcdefg";
str = str.split("").reverse().join("");
映射
映射是一种数据结构,ES6新提出
特点:键名可以不是字符串
声明
let map = new Map();
新增
映射.set(键名,键值)
map.set("name", "张三");
map.set("age", 18);
获取
映射.get(键名)
map.get("name");
函数
可以实现一定的功能
三要素:函数名、参数、返回值
声明函数
字面量(声明式函数)
书写方式:关键字 函数名 小括号 {函数体}
function getSum(a,b){return a+b;} //name:getSum
函数表达式(匿名函数)
书写方式:函数名 赋值符号 function(){函数体}
关键字 函数名 赋值符号 function(){函数体} //(推荐)
let getSum = function(a,b){} //name:getSum
let getSum = function(a,b) F82 {return a+b;} //name:F82
构造函数
书写方式:关键字 函数名 赋值符号 new Function();
let myFunction = new Function();
function sum(a,b){
return a+b;
}
console.log(typeof sum);//function————>函数是引用对象,但是返回类型是function
console.log(sum(1,2));
console.log(sum.name);//sum
let newStu = function F82(){
console.log("我是一个F82函数");
}
newStu();
console.log(newStu.name);//F82
//let a = 0;
//a(); is not a function
参数
形参:形式参数(声明时);实参:实际参数(调用时)
参数情况
当形参与实参的个数不一致时
- 形参个数多余实参个数,多的形参为undefined(声明未赋值,函数声明时就声明了形参,调用函数时才给形参赋值)
- 形参个数少于实参个数
函数名.length可以的得到形参个数函数名.arguments可以的得到所有实参组成的伪数组或类数组(可以用下标去获取数据,但无法通过数组方法的检验)函数名.arguments.length可以的得到实参个数
不定参数
书写格式:...形参A
注意:
- 形参A必须为最后一个形参
- 形参A为多的实参数据
- 不定参数是数组
默认参数:有实参就用实参,没有就用默认值
书写格式: 形参=数据
注意:
- 有默认值的形参之后不再被统计
- 实参为undefined,会触发对应形参的默认值
function myFunction(a,b,...c){
console.log("===========")
console.log(myFunction.length);//函数名.length 可以的得到形参个数(不定参数不计)
console.log(myFunction.arguments.length);//函数名.arguments.length 可以的得到实参个数
console.log(myFunction.arguments);//函数名.arguments 可以的得到所有实参组成的伪数组
console.log(c[1]);//不定参数书写格式:...形参A
return a+b;
}
//不定参数必须写在最后
console.log(myFunction(1,2,3,5));//3
function myFunction2(a,b,c=1){//默认值,有实参就用实参,没有就用默认值
console.log(a+b+c);
}
function F83(a=2,b,c){
console.log(a+b+c);
console.log(F83.length);//有默认值的形参之后不再统计
}
//实参为undefined,会触发对应形参的默认值
F83(undefined,300,3)
返回值
关键字 表达式(返回内容);即返回return后的内容
return 返回值----->会结束函数的执行
注:
- return后的语句不会执行
- 执行到函数的最后,如果没有return,那么返回值就是undefined
箭头函数
写法:
- 省略function
- 如果只有一个形参,则省略小括号
- 如果函数体只有一条语句,则省略大括号
- 如果函数体只有一条语句,且语句是return语句,则省略return和大括号
关键字 函数名 赋值符号 (形参列表)=>{函数体}
(形参列表)=>{函数体}//匿名写法,多用于回调函数
回调函数
功能:函数A作为参数 (函数引用)传递到另一个函数B中,并且这个函数B执行函数A。函数A就是回调函数
function B(A){
A();
}
回调函数的应用(数组方法)
filter
过滤 筛选符合条件(接受书写规则的函数作为参数)的结果,参数callback
let arr = [1, 4, 6, 3, 2, 3, 4, 5];
let res = arr.filter(function (item) {
return item > 3;//filter自己会先遍历,再找出符合规则的元素让其通过组成新的数组返回------>找出arr中大于3的元素
});
let res = arr.filter(item =>item > 3);//简写
sort
排序
//a-b:a在前,b在后 升序
//b-a:b在前,a在后 降序
//会改变原始数组
let temp = arr.sort((a,b)=>a-b);
console.log(temp);
every
如果所有判断的数据条件 都为真 则返回true,否则(只要有一个为假)返回false
let temp1 = arr.every(function (item) {
return item > 3;
});//判断数组中是不是每一个元素都大于3
some
如果有判断的数据条件 都为假 则返回false,否则(只要有一个为真)返回true
let temp1 = arr.some(item => item > 3);//只要有一个大于3就返回true
forEach
遍历数组,无返回值(不影响原数组)
在callback中执行业务代码
注:没有返回值,即返回undefined
arr.forEach(item => {
if (item > 3) {
console.log(item);
}
});
console.log(arr);
map:可以给一个数组的所有元素都施加相同的操作
映射 遍历数组,在callback中执行业务代码,不影响原数组,有返回值(数组)
let res3 = arr.map(item => 2 * item - 1);
reduce可以给一个数组的所有元素都施加相同的操作,再相加返回最终的和
arr4.reduce((total, num) => total + (num * 2 + 1));
IIFE 立即执行函数
功能:声明即调用,调用即销毁
验证码,时间
//官方
(function F82(a, b) {
return a + b;
})(1, 2);
(function F92(a, b) {
console.log(a + b);
return a + b;
}(1, 2));
//隐式,在函数声明前添加!和-等运算符也可以实现立即执行函数
!function F93(a, b) {
console.log(a + b);
return a + b;
}(1, 2);
-function () {
console.log("隐式IIFE");
}();
补充
let array1 = [1, 2, 3,4,5];
let array2 = [3,4,5,6, 7, 8,9,10];
//交集
let temp7 = array1.filter(item => array2.includes(item));
//并集
let temp8 =[ ...(new Set([...array1, ...array2]))];
//数组1对2的差集
let temp9 = array1.filter(item => !array2.includes(item));
[1, 2] + [3, 4] + [5, 6]//1,23,45,6
//解构
//功能:批量赋值
//条件:赋值符号左右的类型要相同
//即:左右都是中括号(数组)或都是大括号(对象)
let [a, b, c] = [1, 2, 3];
console.log(a, b, c);
[a,b]=[b,a];//交换值
对象
对象声明
字面量声明
书写格式:关键字 对象名 赋值符号 大括号
let obj = {};
构造函数声明
书写格式:关键字 对象名 赋值符号 new Object() 分号
let obj = new Object();
对象初始化
注:键值是函数,则键名为对象的方法,反之为对象的属性
书写格式1:关键字 对象名 赋值符号 {
键名1:键值1,
键名2:键值2,
...
键名n:键值n
};
//示例1
let person = {
username: '张三',
age: 18,
hobby: ['篮球', '足球', '羽毛球'],
sing: function () {
console.log('唱歌');
},
play(){
console.log("玩游戏");
},
intro:()=>console.log("你好!")
};
//示例2
let computer = {
brand: '联想',
price: 5000,
color: '银色',
video: function () {
console.log('播放视频');
},
playGame: function () {
console.log('玩游戏');
},
study() {
console.log('学习');
}
};
对象的使用
属性的访问格式
- 对象名.属性名;
- 对象名[属性名];(属性名为字符串,中括号里可以传存字符串的变量进去)
方法的调用格式
对象名.方法名();
console.log(person);//{username: "张三", age: 18, hobby: Array(3), sing: ƒ}
person.age;
person[`age`];
person.sing();
console.log(person.sing());//唱歌 undefined 因为sing是函数,没写返回值 所以返回undefined
新增(修改)键值对
新增键名在对象中有就是修改,没有就是新增
-
对象名.新增键名 赋值符号 键值
-
对象名[新增键名] 赋值符号 键值
注意:中括号内的类型必须是字符串
- 对象名['新增键名'] 赋值符号 键值
- let 变量名 = '键名';对象名[变量名] 赋值符号 键值
Symbol
Symbol是基本数据类型
作用:实现对象新增属性时不覆盖对象当中原始的键值对
let temp1 = Symbol();
console.log(typeof temp1);//symbol
let age = Symbol('age');//括号内是描述变量的内容,一般和变量名一致
obj2[age] = 20;
console.log(obj2);//{age: 20, name: "李四", hobby: Array(3), sing:... [Symbol(age)]: 20}
console.log(obj2.age,obj2[age]);//18,20
查(获取)
-
以点的方式:对象名.属性名
-
以中括号的方式:对象名[属性名]----->确保中括号里面的属性名是字符串
-
in判断对象中是否存在要查找的键名书写格式:
键名 in 对象名
console.log('age' in obj2);//true,注意书写键名用字符串
删除——删对象中存的键名
delete 对象名.键名
delete obj2.age;//删除对象的属性
delete obj2.sing;//删除对象的方法,注意方法后不要跟小括号
遍历对象
不含symbol的键名
//遍历对象键名
for (let key of Object.keys(obj2)) {
console.log(key);
}
for (let k in obj2) {
console.log(k);
}
//遍历对象键值
for (let value of Object.values(obj2)) {
console.log(value);
}
//遍历对象键值对
for (let arr of Object.entries(obj2)) {
console.log(arr);
}
//遍历键名找值
for(let key in obj2){
console.log(key,obj2[key]);
}
含symbol的键名
console.log(Reflect.ownKeys(obj2));//["name", "hobby", "sing", "play",Symbol(age)]
this关键字
普通对象中,谁调用我,我就是谁(指代当前对象)
let obj3 = {
username: "z3",
age: 18,
city:"北京",
intro: function (){
console.log(`大家好,我是${this.username},我今年${this.age}岁,来自${this.city}`);
}
}
obj3.intro();//大家好,我是z3,我今年18岁,来自北京
let obj4 = {
username: "z4",
age: 19,
city:"上海"
}
obj4.hello = obj3.intro;//址传递
obj4.hello();//大家好,我是z4,我今年19岁,来自上海
内置对象
Math
常用:
向上取整: Math.ceil(value)
向下取整:Math.floor(value)
随机数:Math.random() 得到[0,1)的随机数
取最大值:Math.max(values)
取最小值:Math.min(values)
保留几位小数(自带四舍五入):value.toFixed(位数);
Date
//创建时间对象
let date = new Date();
//获取年份
console.log(date.getFullYear());
//获取月份,注意计算机里面的月份是0~11
console.log(date.getMonth() + 1);
//获取一个月中的第几天
console.log(date.getDate());
//获取星期
console.log(date.getDay());
//获取时
console.log(date.getHours());
//获取分
console.log(date.getMinutes());
//获取秒
console.log(date.getSeconds());
console.log(date.toString());//Mon Jun 13 2022 14:51:23 GMT+0800 (中国标准时间)
console.log(date.toDateString());//获取日期,不包含时间 Mon Jun 13 2022
console.log(date.toTimeString());//14:51:23 GMT+0800 (中国标准时间)
console.log(date.toLocaleDateString());//获取本地日期,不含时间 2022/6/13
console.log(date.toLocaleString());//获取本地时间(年/月/日 时:分:秒)2022/6/13 14:51:23
console.log(date.getTime());//获取时间戳
String
自动封箱、自动拆箱
-
获取字符串长度
str.length -
获取第n个字符,注:n为非数字,则转换为0
str.charAt(index) -
合并字符串
str.concat(str2) -
批量获取
字符串.slice(起始下标,结束下标)注意不包含结束下标
str = `zbhjahduiiwe`; console.log(str.slice(1, 3));//bh console.log(str.slice(5,2));//空字符串-
字符串名.substr(开始下标,个数)substr()出现负数,则字符串长度与其相加console.log(str.substr(1, 3));//bhj -
字符串名.substring(开始下标,结束下标)注意不包含结束下标注:1、substring出现负数,则自动转换为0;2、substring第二个参数为负数,则自动转换为0,并与第一个参数互换
console.log(str.substring(1, 3));//bh console.log(str.substring(5,2));//bhj 2,5自动交换位置
-
是否以xxx开始,返回布尔值
str.startsWith("xxx")console.log(str.startsWith("zbh"));//true console.log(str.startsWith("bhj"));//false -
是否以xxx结束,返回布尔值
str.endsWith("xxx")console.log(str.endsWith("we"));//true console.log(str.endsWith("wee"));//false -
去空格
-
trim()去除前后空格,不会改变原字符串,需要接受返回值(新字符串)str = " 123 "; console.log(str.length);//9 console.log(str.trim());//去空格 123 -
trimLeft()/trimStart()去除前面(左边)空格 不会改变原字符串,需要接受返回值(新字符串)console.log(str.trimLeft()); str = str.trimStart(); console.log(str.length);//6 -
trimRight()/trimEnd()去除后面(右边)空格 不会改变原字符串,需要接受返回值(新字符串)console.log(str.trimRight()); str = str.trimEnd(); console.log(str.length);//3
-
-
大小写转换,不改变原字符串
str.toUpperCase()小转大str.toLowerCase()大转小
str = 'jdiwhfAMDKLSJDf'; console.log(str.toUpperCase());//小转大 console.log(str); console.log(str.toLowerCase());//大转小 -
重复参数个字符串
console.log(str.repeat(2)); -
查找字符串中的字符串
-
indexOf(): 属性返回字符串中指定文本首次出现的索引(位置) -
lastIndexOf():属性返回字符串中指定文本最后一次出现的索引(位置)注意:
-
如果未找到文本,indexOf()和lastIndexOf() 均返回 -1
-
两种方法都接受作为检索起始位置的第二个参数:
-
lastIndexOf() 方法是向后进行检索的(从后往前),如例子中的第二个参数是6,则是从索引为6的地方开始向前检索直到字符串的起点。
-
-
search():属性返回字符串中指定字符串的首次出现的索引(位置)
-
正则表达式
正则表达式RegExp:Regular Expression
功能:描述一个字符串的匹配方式,即判断用户输入的内容是否符合我们的要求
声明正则表达式
-
字面量
关键字 正则名 赋值符号 /规则/修饰符
修饰符取值:
-
g:global全局匹配
-
i:insensitive大小写不敏感(即不区分大小写)
-
m:multiline多行匹配
注:修饰符即条件;修饰符可以组合使用,无优先顺序
let reg = /a/gim; -
-
构造函数
关键字 正则名 赋值符号 new RegExp("规则","修饰符")
let reg1 = new RegExp("[1]","gim");
两个方法
-
字符串.match(正则表达式)返回满足正则的内容.如果没有满足的内容,则返回null -
正则.test(字符串)返回布尔值
按位比较
书写格式:[查找的内容] 内容可以1个或多个,无分隔符(如果连续的数字或字母,推荐使用连字符)
str = `23asdBAasafdA`;
let re = /[a-z][1-9]/ig;//以第一位是字母,第二位是数字的方式查找
console.log(re.test(str));//false
console.log(str.match(re));//null
开始和结束
以指定内容开始
书写格式:^[开始的内容] 内容可以是多个或多个,无分隔符
注:如果查找的内容是连续的则可以用连字符-来代替中间内容
re = /^[a-z]/ig;//以字母开头
以指定内容结束
书写格式:[结束的内容]$ 内容可以是多个或多个,无分隔符
re = /[a-z][1-9]$/ig;//
let str2 = `asdBAasdA3`;
console.log(re.test(str2));//true
不以指定内容开始
书写格式:^[^不能开始的内容] 内容可以是多个或多个,无分隔符(如果连续的数字或字母,推荐使用连字符)
扩展——某一位不包含指定内容
书写格式:[^不包含的内容] 内容可以是多个或多个,无分隔符(如果连续的数字或字母,推荐使用连字符)
不以指定内容结束
书写格式:[^不能结束的内容]$ 内容可以是多个或多个,无分隔符(如果连续的数字或字母,推荐使用连字符)
量词
{个数}
功能:返回满足个数的内容
str = `aaaaaaaaaaaa`;
re = /a{5}/ig;
console.log(str.match(re));//["aaaaa"]["aaaaa"]
{min,max}贪婪匹配
功能:先匹配max个内容,再匹配max-1个内容,直到最小值
re = /a{2,5}/ig;
console.log(str.match(re));//["aaaaa"]["aaaaa"]["aa"]
元字符
- \d 0-9
- \D 非0-9
- \w 字母、数字、下划线
- \W 非 字母、数字、下划线
- \s 空白符(空格、回车)
- \S 非空白符
扩展
{n,}获取n到正无穷的内容{1,}获取1到正无穷可以用”+“ 例如/[a]+/{0,1}获取0个到1个可以用”?“ 例如/[a]?/加上全局利用match返回最后会有一个''{0,}获取0个到正无穷可以用”*“ 例如/[a]*/加上全局利用match返回最后有一个''
### 匹配有条件的内容
-
n(?=m)功能:查找后面是m的n
-
n(?!m)功能:查找后面不是m的n
命名规范
- 不能以数字开头
- 不能使用关键字和保留字
- 不能使用中文
命名方式
- 约定俗成
- 小驼峰 (推荐)
- 大驼峰 (有特殊含义,比如构造函数)
- 蛇形命名法 “_下划线”
- 匈牙利命名法 “S_name ” "N_index"
- 见名知意
保留字
abstract await boolean break byte case catch char class const continue debugger default delete do double else enum export extends false final finally float for function goto if implements import in instanceof int interface let long native new null package private protected public return short static super switch synchronized this throw throws transient true try typeof var volatile void while with yield