1.JavaScript入门
1.1简介
javascript简称js,是基于对象和事件驱动的客户端脚本语言。
ECMAScript5.0 ECMAScript6.0简称ES5 ES6
javascript和java有什么关系?
没有关系
雷锋和雷峰塔
仙女和仙女山
老婆和老婆饼
javascript能做什么?
网页特效
表单验证(正则)
游戏编写
编写Node
1.2javascript的引入方式
直接引入
<script>js代码</script>
<script type="text/javascript">js代码</script>
<script language="javascript">js代码</script>
外部引入
<script src="url地址"></script>
注意:外部引入的script标签内的代码不生效
js的引入位置:js可以在任意地方引入,除了title标签
建议将js代码放置在body的内容之后,如果放置在head中,若js代码过大,可能会导致一段时间的网页空白。
1.3js常见的几种输出方式
方式一:弹框输出
alert();
方式二:文档流输出
document.write();
方式三:控制台输出
console.log();
js的注释方式
注释不会被浏览器解析,起到解释说明的作用,方便代码调试。
注意:注释内不要嵌套注释
1.4js的变量
变量是一个数据结构(可以改变的量),可以存放任何的数据类型
变量定义的方式:var 变量名;
var 是js的系统关键字(常见的系统关键字if else var continue break let const)
变量名的命名规范:
1、采用数字、字母、下划线以及$组成,但不能以数字开头
2、js中严格区分大小写
3、js中可以使用中文,但是不建议使用
4、不能使用系统关键字命名(if else var continue break)
注意:Unexpected token ‘break’
5、推荐驼峰命名法 firstName firstChild girlFriend firstElementChild name age time
注意:var声明的变量存在变量提升(声明提前,但是赋值并未提前)
<script>
console.log(apple);
var apple="iphone";
</script>
运行结果为:
变量提升:代码在执行的时候,会将"var apple"这句语句提升在console之前。
2.常见数据类型
方式一:一种数据类型(了解)
? 对象(object)js中到处都是对象,就算本身不是对象,在运算的过程中都会转换为对象
方式二:两种数据类型
? 1、值类型(undefined、string、number、boolean、null)
? 2、引用类型(object)
方式三:六种数据类型(重点)
未定义类型undefined
字符串类型String
布尔类型Boolean true false
数值类型Number(科学计数法、十六进制、无穷、除数、被除数、整型、浮点型)
空类型Null(object)
对象类型Object(object function)
对象的所属关系 instanceof,返回boolean值
检测数据类型typeof
方式一:typeof(被检测的变量)
方式二:typeof 被检测的变量
2.1undefined类型
什么情况下会出现undefined?
1、变量声明后未赋值,值为undefined
2、直接将变量的值赋值为undefined
3、函数的参数未传入实际的值,该参数未undefined
4、函数运行后,未给出返回值(return),则未undefined
5、对象的属性未进行定义,值也是undefined
<script>
var num;
console.log(num)
var num=undefined;
console,log(num)
function fun(a,b){
console.log(a,b)
}
fun(1)
var res = fun(1,2)
console.log(res)
console.log(typeof res)
var obj = new Object();
console.log(obj.age)
</script>
2.2null类型
null空对象指针
null和undefined的区别
? 1、类型不同
Null为空对象指针,为object类型,undefined的类型为Undefined
? 2、undefined未定义类型,以后可以装任意的数据类型;而null为空对象指针,但以后接收对象类型
<script>
var nu = null;
console.log(typeof nu)
console.log(null == undefined);
console.log(null === undefined);
</script>
2.3string类型
在js中,采用引号定义字符串
注意:js中不区分单双引号,建议使用单引号。主要是为了和html中的双引号做区分。
注意:
1、 转义字符 ‘\’
2、js的连接符 '+'
var name = 'cdd';
var age = 18;
var newStr = name+'说:“我今年'+age+'岁”'
console.log(newStr)
var str = "<p stylle=\"color:red\"></p>";
console.log(str)
2.4boolean类型
boolean主要用于后期做判断使用
主要分为两个值:true(真) false(假)
注意:当boolean进行计算的时候,true自动转化为1,false自动转换0
2.5number类型
(1)在js中不严格区分整型和浮点型,类型均为number
整型 (占4个字节) 取值范围为-2的53次方到2的53次方
浮点型(小数) (占8个字节)
注意:当整型超过取值范围,自动转换为浮点型
var num = 10.00100;
console.log(num)
console.log(typeof num)
(2)进制
二进制:逢二进一 0 1
八进制:逢八进一 0-7
十进制:逢十进一 0-9
十六进制:逢十六进一 0-9 a-f
10 a 11 b 12 c 13 d 14 e 15 f
数字采用0开头,首先考虑八进制,若后面数字超过7,则该数字为十进制
0x代表十六进制,在进制内不区分大小写
var num = 023;
var num = 029;
var num = 0xb;
var num = 0xB;
console.log(num)
console.log(typeof num)
(3)科学计数法
e代表的是10的多少次方
例如 e3代表 101010 10的3次方
e-3代表 1/(101010) 10的3次方分之一
var num = 3.14e2;
var num = 3.14e-2;
console.log(num)
console.log(typeof num)
(4)无穷Infinity
当除数为0的时候,会出现Infinity,但是程序不会终止,类型为number
var num = 0/10;
var num = 10/0;
console.log(num)
console.log(typeof num)
(5)小数计算
单精度 双精度的影响
console.log(0.1+0.2);
console.log(0.2+0.1 == 0.3)
console.log(0.2+0.3 == 0.5)
console.log(1+2 == 3)
(6)NaN
NaN是如何产生的呢?(重点知道如何解决)
——通过运算希望得到一个数值类型,但是最终却没得到(比如价格的计算)
NaN是一个连自己都不认识自己的数值类型
只要NaN参与运算,其结果都为NaN
var num = 2 * '你好';
var num = 2 * '200px';
var num = 2 * '200';
var num = 10 + '10';
console.log(num)
console.log(typeof num)
console.log(NaN == NaN)
console.log(NaN === NaN)
var num = NaN + 3;
var num = NaN - 3;
var num = NaN * 3;
var num = NaN / '3';
console.log(num)
2.6object类型
对象 object
(1)通过实例化生成对象new Object() 生成的对象叫做实例化对象
var obj = new Object();
obj.name = 'cdd';
obj.play = function(){
}
(2)通过字面量(json)去定义
var obj = {};
var person = {
name:'张三',
age:30,
say:function(){
console.log('三十而立')
}
}
对象的属性-----------------------变量
obj.属性名 = 属性值;
对象的方法----------------------函数
obj.方法名 = function(){
}
var name='cdd';
console.log(window.name)
var obj=new Object();
console.log(obj);
console.log(typeof obj)
var cat={
name:'tom',
gender:'boy',
hobby:function(){
console.log('eat!')
}
}
console.log(cat.name,cat.gender)
cat.hobby()
3.类型转换
隐式转换(自动转换)
强制转换
3.1隐式转换
注意:
1、纯数字的字符串在运算时,会自动转换为数值进行计算(除了+,’+'作为连接符使用)
2、布尔类型的值在运算时,true相当于1,false相当于0
3、只有空字符串(’’)会转换为false,只要有内容,则会转为true
4、数值类型除了0以外其余都转换为true(除了NaN),0将转换为false
tofixed(n)设置固定的小数位数 n代表小数点后保留几位
<script>
var res=5*'5';
var res=5+'5';
var res=2+true;
console.log(res)
console.log(typeof res)
</script>
3.2强制转换
强转为Boolean
var str=5;
var str=0;
var str='abc';
var str=' ';
var str='';
var str=undefined;
var str=null;
var res=Boolean(str)
console.log(res)
强转为字符串
String()
var res=String(num);
toString()建议使用
num.toString()
强转为数值类型(重点)
**parseInt()**强制转换为整型(重点)
? 解析进制(默认解析十六进制,不解析八进制)
? 小数转换为整型时,直接去除小数点后面的内容
? 解析字符串(解析第一个字母之前的数值,之前没有数值则为NaN)
扩展:
parseInt(string,radix) radix为基数,取值2-32
parseFloat()
? 不解析进制
? 解析字符串(解析第一个字母之前的数值,之前没有数值则为NaN)
? 解析小数,但只保留第一个小数点
Number()
? 解析进制(十六进制)
? 只解析纯数字的字符串(带字母不解析)
测试:
<script>
var num=9.1;
var num=9.9
var num='0xa';
var num='023';
var num='123abc';
var num='1a2b3c';
var num='abc123';
var num='3.14a';
var res=parseInt(num);
console.log(res);
var str ='023';
var res=parseInt(str);
var res=parseInt(str,0);
var res=parseInt(str,8);
var res=parseInt(str,16);
console.log(res)
</script>
var str='0xa'
var str='123abc';
var str='3.14a';
var str='3.14.115'
var res =parseFloat(str);
console.log(res);
var num=36.00;
console.log(num)
var num=25;
var num=3.1415925;
var num=9.99999;
var res=num.toFixed(2);
console.log(res)
var str='0xa';
var str='123adc';
var str='123';
var res=Number(str);
console.log(res);
以上总结:
| parseInt() | parseFloat | Number() | toFixed() |
---|
解析进制 | 是,但不解析八进制 | 否 | 是,不解析八进制 | 否 | 解析字符串 | 是 | 是 | 是 | 否 | 解析数 | 是,向下取整 | 是 | 是 | 是 |
4.运算符
数学运算符 + - * / %(取余) ++ –
%计算的结果的余数
+ 注意作为连接符使用的情况
a++ 先将a的值参与运算,再将其加一
++a 先将a的值加一,再将加一后的结果参与运算
?
a-- 先将a的值参与运算,再将其减一
–a 先将a的值减一,再将减一后的结果参与运算
var a = 10;
var res = a++ + a++;
console.log(res)
var a = 10;
var res = ++a + a++;
console.log(res)
var a = 10;
var res = a++ + --a;
console.log(res)
赋值运算符 = += -= *= %=
比较运算符 > < >= <= != == (恒等) ===(全等)
三元运算符 (条件)? 成立时执行的代码 : 不成立时执行的代码
逻辑运算符
与 && 两者为真则为真,只要有假则为假
或 || 两者为假则为假,只要有真则为真
非 ! 真->假 假->真
逻辑运算符中存在逻辑短路
逻辑短路:当前面的条件可以直接判断出结果,则后面的条件将不会执行
注意:尽量把重要的先决条件放在前面
位运算符(了解)
位运算符:将值先转换为二进制,再按位计算
与 & 两者为真则为真,只要有假则为假
或 | 两者为假则为假,只要有真则为真
非 ~ 真->假 假->真
console.log(2&3)
console.log(2|3)
console.log(7&8)
console.log(7|8)
console.log(~5)
console.log(~-6)
5->0101->补码:0101->补码+1:0110->给上符号位:-6;
-6->0110->补码:1001+1->1010->取反:0101->5
概念总结: 原码为正数,内存中的补码也为正数,按位取反后内存中的补码变为负数,当内存中的补码转化成原码时,原码等于=补码除符号位外逐位取反,并在最低位+1。 原码为负数,内存中的补码为原码的除符号位外逐位取反,并在最低位+1,按位取反后内存中的补码变为正数,当内存中的补码转化成原码时,原码=补码。
5.流程控制
条件判断
单向分支:如果符合条件则执行,不符合则跳过
if(条件){
}
双向分支
if(条件){
条件成立时执行
}else{
条件不成立时执行
}
多向分支
if(条件){
成立时执行
}else if(条件){
成立第二个条件时执行
}else{
条件均不成立时执行
}
switch…case
switch(条件){
case 分支:
break;
case 分支:
break;
//当所有的case都不满足时执行 一般放置在所有的case后面
default:
break;
}
循环
for循环(显示迭代)
for(初始值;判断条件;改变条件){
循环体
}
常见的例子:
for(var i=0;i<5;i++){
console.log(i)
}
循环中的关键字
break:终止整个for循环,后面的内容将不会执行
for(var i=1;i<10;i++){
// 如果满足条件则执行,不满足则跳过
if(i%2==0){
// 跳出整个循环体(跳出整个for循环,for循环的代码到此结束)
break;
}
console.log(i)//1
}
continue:结束当前循环,继续执行下一个循环
for(var i=1;i<10;i++){
// 如果满足条件则执行,不满足则跳过
if(i%2==0){
//跳出本次循环,继续执行下一个循环
continue;
}
console.log(i)//1 3 5 7 9
}
while循环
while(判断条件){
循环体
}
示例:
var i=0;
while(i<=10){
console.log(i);
i+=2;
}
do…while循环
do{
循环体
}while(判断条件)
var num = 5;
do{
console.log(num)
}while(num>10)
注意:
while是先判断再执行循环体内容
do…while是先执行一次循环体,再进行判断
6.函数
函数的概念:函数是一小块代码的封装,要求功能越独立越好,功能越强大越好。
6.1函数的定义
1、标准定义方式
function 函数名(参数){
函数体
}
function fun(){
console.log('标准函数定义')
}
注意:函数可以在任意的地方调用
2、赋值的方式
var 函数名 = function(参数){
函数体
}
fun()
var fun = function(){
console.log('通过赋值方式定义')
}
注意:赋值方式定义的函数只能在赋值之后才能调用
3、原生方法定义(了解,不建议使用)
var 函数名 = new Function(函数的具体内容);
var fun = new Function('console.log("原生方法定义")');
函数的调用:将函数体内的代码从上往下执行一遍
函数名(); 例如:fun() demo(实参)
6.2匿名函数
函数重名问题
当在一个js中,标准方式定义的函数名相同时,后面的函数会自动覆盖前面定义的函数,在任何地方都没法调用
注意:函数命名时,不能和系统函数重名
匿名函数
匿名函数:没有名字的函数
匿名函数的特点:
1、避免了函数取名的困扰
2、匿名函数永远不会被其他函数重写
3、匿名一般情况下,只调用一次。定义时则直接调用
(function(){
console.log('匿名函数')
})();
函数的参数(重点)
函数的参数
形参-----------形式参数(定义函数时小括号内的参数为形参)
实参-----------实际参数(调用函数时,小括内的参数为实参)
function 函数名(形参1,形参2...){
函数体...
}
函数名(实参1,实参2...);
注意:形参和实参的个数不一定要相等
形参和实参的个数问题?
1、函数给出形参,但未传入实参
function fun1(a){
console.log(a)
}
fun1();
2、函数给出的形参个数大于实参个数
function fun2(a,b,c){
console.log(a,b,c)
}
fun2(1,2)
3、函数给出的形参个数等于实参个数(常规情况)
function fun3(a,b){
console.log(a,b)
}
fun3(10,20);
4、函数给出的形参个数小于实参个数
function fun4(a){
console.log(a)
}
fun4(1,2,3)
5、函数给出实参,但未给出形参
function fun5(){
console.log(arguments)
console.log(arguments[2])
}
fun5('胡桃','甘雨','魈')
注意:系统有一个arguments可以接收所有的实参
6.3函数的返回值return
注意:console.log()只是输出,函数的返回值只和return有关
函数的返回值的几种情况
1、函数调用后未给出return返回值,则调用后的结果为undefined
function fun1(){
console.log('测试代码:不给返回值')
return
}
var res = fun1()
console.log(res)
2、函数调用后通过return返回值(可以为任意数据类型,变量,表达式)(重点)
函数调用的结果则为函数返回值(return后面的内容)
function fun2(){
var name = '张羿'
return name+'会射太阳吗';
}
var res = fun2()
console.log(res)
function fun3(){
return {name:'张三',sex:'男'};
}
var res = fun3()
console.log(res)
function fun4(){
function fun(){
console.log('张三丰')
}
return fun;
}
var res = fun4()
console.log(res)
res()
3、return后面的代码不执行
function fun3(){
console.log('我不想看到你')
return 111;
console.log('看看我在不在')
}
var res = fun3();
console.log(res)
4、函数调用后可以给出返回值,也可以不给(return不是必须的)
6.4函数的变量
**作用域:**变量的作用范围(使用的范围的大小)
全局变量:
? 定义:在函数体的外部定义的变量(推荐),或者在函数体内部不采用var声明的变量(但是不推荐此写法)
? 作用域:作用范围广,可以在任意地方均可以访问和修改,故叫做全局变量。只有整个js文件运行结束后,全局变量才销毁。
? 注意:一旦全局变量被更改,所有使用的地方都会被影响。所以合理使用(全局变量污染)。
局部变量:
? 定义:在函数体的内部采用var定义的变量
? 作用域:作用范围只在函数体的内部,作用范围小,故叫做局部变量。函数执行完成后,局部变量则被销毁
? 注意:
? 建议能使用局部变量则尽量使用局部变量
? 不同的函数之间,局部变量名可以重复使用
? 当全局变量和局部变量发生冲突时,优先使用局部变量
函数的作用域链
? 函数的作用域链:变量是(从内往外)一级一级的向上查找(父级函数),直到找到为止,反之不成立
? 函数查找变量的方式:
1、先查找当前函数是否具有该变量,则使用该变量
2、若当前函数没有,则向父级函数查找是否有该变量,若有,则使用改变量
3、若直到找到最大的作用域,没发现该变量,则系统认为该该变量不存在
6.5回调函数
回调函数(重点)
定义:形参中至少有一个是已定义好的函数
回调的意义:我们可以在函数的内部调用其他函数(且函数名还可以切换)
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title></title>
</head>
<body>
<script>
function add(a,b){
if((a>0&&a<1)||(b>0&&b<a)){
var l1=a.toString().split(".")
var l2=b.toString().split(".")
var lenth=Math.max(l1[1].length,l2[1].length)
return ( a*Math.pow(10,lenth)+b*Math.pow(10,lenth))/Math.pow(10,lenth)
}
else
return a+b;
}
function minus(a,b){
return a-b;
}
function multiply(a,b){
return a*b;
}
function divde(a,b){
if(b==0){
console.log('除数不能为0!')
}
else
return a/b;
}
function calculator(a,b,method){
return method(a,b);
}
var res=calculator(0.1,0.2,add)
console.log(res)
</script>
</body>
</html>
6.6闭包函数(重点)
(重点:注意笔试面试考闭包的概念)
闭包函数:内部函数在其作用域外被调用,则形成了内部函数的闭包
若闭包函数使用了全局变量,则该变量所占的内存不会被释放。直到整个js运行结束。
闭包函数的特点:
优点:内部的函数可以在其作用域之外被访问
缺点:占内存,可能存在内存泄漏,慎用闭包。除非必须使用某个局部变量
解决方案:在内部函数调用完成之后,将该内存释放。(将该变量赋值为空)
function outside(){
var num = 100;
var inside = function(){
num++;
console.log(num)
}
return inside;
}
var res = outside()
console.log(res)
res()
outside()
res();
outside()
res();
var res = outside()
res()
res = null;
6.7递归
定义:自己调用自己
function fun(n){
console.log(n)
if(n>0){
fun(n-1)
}
}
function fun(n){
console.log(n)
if(n>0){
fun(n-1)
}
console.log(n)
}
fun(3)
递归理解:
function fun(2){
console.log(2)
if(2>0){
console.log(1)
if(1>0){
console.log(0)
if(0>0){
}
console.log(0)
}
console.log(1)
}
console.log(2)
}
递归实现阶乘
方法一:
var num = 1;
function fun(n){
if(n>1){
num*=n;
fun(n-1)
}else{
return 1;
}
return num;
}
var res = fun(3);
console.log(res)
方法二:
function fun(n){
if(n==0 || n==1){
return 1
}
else if(n>1){
return n* fun(n-1)
}
else{
return '你输入的数的格式不合理'
}
}
let res=fun(10)
console.log(res)
7.对象
7.1认识对象
创建对象
var obj = new Object();
查看对象原型
console.log(obj.__proto__);
console.log(Object.prototype)
注意:constructor为对象的构造函数
在对象原型下添加方法
Object.prototype.play = function(){
console.log('张家界去不得');
}
原型链:从当前实例化对象开始一级一级向上查找原型,最顶层对象原型为Object.prototype,而Object.prototype的原型为null,没有任何属性和方法
instanceof
instanceof 查看对象原型所属关系,返回一个boolean值
<script type="text/javascript">
var arr =new Array()
console.log(typeof arr)
var str =new String()
console.log(typeof str)
console.log(arr instanceof Array)
console.log(arr instanceof String)
console.log(str instanceof String)
console.log(str instanceof Array)
console.log(str instanceof Object)
console.log(arr instanceof Object)
</script>
7.2数组
数组定义
方式一:
var arr = new Array();
var arr = new Array(5);
console.log(arr)
var arr = new Array('cdd');
console.log(arr)
var arr = new Array(1,2,3);
console.log(arr)
方式二:
var arr=[]
length为数组的长度
数组的下标为数字,默认从0开始递增
数组最大的下标+1=数组的长度
7.3数组的CRUD
访问数组内的值(通过其下标访问)
arr[i] i代表指定的下标
添加指定下标的值
arr[]={'胡桃','甘雨'}
arr[2]='魈'
console.log(arr)
修改指定下标的值
arr[]={'胡桃','甘雨'}
arr[0]='魈'
console.log(arr)
删除指定下标的值 delete() splice()
注意:
1,delete只是将对应下标的值进行删除,保留键
2,splice(start,num)删除 ,该删除不保留键
- ? start 删除的起始下标
- ? num 删除的个数
?
arr[]={'胡桃','甘雨'}
delete(arr[0])
console.log(arr)
arr.splice(0,1)
console.log(arr)
7.4数组遍历
显示迭代:
for(var i=0;i<arr.length;i++){
console.log(arr[i])
}
隐式迭代
arr.forEach(function(val,key,ownObj){
})
对象的遍历(重点)
for...in...
语法:for(var 变量名 in 遍历的对象){
}
注意:该变量名则为对象的属性名和方法名(键)
for(var key in obj){
console.log(key)
console.log(obj[key])
练习:去除数组中的undefined,null
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title></title>
</head>
<body>
<script type="text/javascript">
let arr=[1,2,3,undefined,undefined,6,undefined,9,undefined,null]
function clear(arr){
let list=[];
for(let i=0;i<arr.length;i++){
if(typeof arr[i] == 'number'){
list.push(arr[i])
}
}
return list
}
let res=clear(arr)
console.log(res)
</script>
<script type="text/javascript">
let arr1=[1,2,3,undefined,undefined,6,undefined,9,undefined,null]
function clear(arr){
arr.sort()
let n=0;
for(let i=0;i<arr.length;i++){
if(typeof arr[i] !=typeof arr[i+1]){
n=i+1
break;
}
}
arr.splice(n,arr.length)
return arr
}
let res1=clear(arr1)
console.log(res1)
</script>
<script type="text/javascript">
let arr3=[1,2,3,undefined,undefined,6,undefined,9,undefined,null]
function clear(arr){
let list2=[];
arr.forEach(function(value,i){
if(typeof arr[i] == 'number'){
list2.push(arr[i])
}
})
return list2
}
let res3=clear(arr3)
console.log(res3)
</script>
</body>
</html>
7.5数组函数
函数三要素:功能、参数、返回值
cancat()
***concat()**连接两个或更多的数组,并返回结果
var a=['胡桃','甘雨','魈']
var b=['琴','芭芭拉','迪卢克']
var c=['万叶','神里']
var arr=a.concat(b)
console.log(arr)
var arr =a.concat(c,b,'埃洛伊')
console.log(arr)
join()
***join(指定的字符)**将数组按照指定的字符拼接成字符串(将数组转换为字符串) 注意:join默认按照’,'进行拼接
var arr =['埃','洛','伊','将','被','免','费','赠','送']
var str=arr.join()
var str=arr.join('')
console.log(str)
数组入栈、出栈
***push()**向数组的末尾添加一个或更多元素,并返回新的长度(多个元素采用逗号连接) ***pop()**删除并返回数组的最后一个元素(不需要传参) ***unshift()**向数组的开头添加一个或更多元素,并返回新的长度.(多个元素采用逗号连接) ***shift()**删除并返回数组的第一个元素(不需要传参)
var arr =['胡桃','甘雨','魈','芭芭拉','菲谢尔']
arr.push('优菈')
arr.pop()
arr.unshift('空')
arr.shift()
console.log(arr)
slice()
***slice(start,end)**数组的截取 slice(start)(第一个参数必填)从指定下标(start)开始截取,截取到最后 slice(start,end)从指定下标(start)开始截取,截取到指定结束下标(end)之前 注意: 1、在截取数组时,包含起始下标(start),不包括结束下标(end) 2、截取的下标可以为负数,代表倒数第几个 3、slice截取为从左往右截取
var arr=[1,2,3,4,5]
console.log(arr)
console.log(arr.slice(1))
console.log(arr.slice(-1))
console.log(arr.slice(1,4))
console.log(arr.slice(-3,4))
console.log(arr.slice(-4,-1))
splice()
***splice(index,num,item)**删除、修改或者添加数组的元素 (改变原数组) index:代表从指定的索引(下标)开始 num:删除的个数 splice(index,num)从指定的下标(index)开始,删除num个 splice(index,num,item)从指定的下标(index)开始,将指定的num个的内容替换为item 注意:splice和delete删除不同点: splice删除数组的值,不保留键 delete删除数组的值,保留键(此时对应的下标的值为undefined)
splice可以接收返回值,返回值为数组,返回被删除的内容
var arr =['胡桃','甘雨','魈','芭芭拉','菲谢尔']
arr.splice(1,2)
console.log(arr);
var arr =['胡桃','甘雨','魈','芭芭拉','菲谢尔']
arr.splice(0,2)
console.log(arr);
var arr =['胡桃','甘雨','魈','芭芭拉','菲谢尔']
arr.splice(1,1,'莫娜')
console.log(arr);
var arr =['胡桃','甘雨','魈','芭芭拉','菲谢尔']
arr.splice(1,0,'莫娜')
console.log(arr);
reverse()
**reverse()**反转,颠倒数组元素的排序
let arr=[1,2,3,4]
console.log(arr.reverse())
sort()
**sort()**对数组的元素进行排序(按照ASCII的码值进行排序) sort(sortby)了解 sortby必须为一个函数
let arr2=[12,1,2,45,22,11,0]
function esc(a,b){
if(a>b){
return 1;
}else if(a==b){
return 0;
}else if(a<b){
return -1;
}
}
console.log(arr2.sort(esc))
let arr3=[12,1,2,45,22,11,0]
function desc(a,b){
if(a>b){
return -1;
}else if(a==b){
return 0;
}else if(a<b){
return 1;
}
}
console.log(arr3.sort(desc))
indexOf()
***indexOf()**查找指定元素在数组中第一次出现的位置 如果该元素存在数组中,则返回该元素的下标,若不存在则返回-1
***lastIndexOf()**查找指定元素在数组中最后一次出现的位置
var arr=['胡桃','甘雨','莫娜','七七','莫娜']
console.log(arr.indexOf('七七'))
console.log(arr.lastIndexOf('莫娜'))
console.log(arr.indexOf('凝光'))
拓展ASCLL
注意:默认按照ASCII的码值从小到大排序 资料:ASCII的介绍 http://ascii.911cha.com/ 拓展:0-9 编码为48-57 A-Z 编码为65-90 a-z 编码为97-122
ES6的数组函数: map filter
7.6字符串函数
length
字符串中的length属性 语法:str.length
字符串的查找
字符串查找指定下标的值(es6中使用) str[index] index为指定的下标
字符串的查找 **charAt(index)**获取指定下标对应的值(index为下标,默认从0开始) 注意:若index的值超过0到字符串的长度,则返回的值为空字符串
**charCodeAt(index)**返回在指定的位置的字符的 Unicode 编码(ASCII码值)
**fromCharCode(num)**可接受一个指定的 Unicode 值,然后返回一个字符串 语法: String.fromCharCode(num) num为unicode编码
(indexOf lastIndexOf重点内容) ***indexOf()**查找指定字符第一次出现的位置 ***lastIndexOf()**查找指定字符最后一次出现的位置
var str='什么?稻妻的雷神竟然有两个?'
console.log(str)
console.log(str[0])
console.log(str.charAt(0))
console.log(str.charCodeAt(0))
console.log(String.fromCharCode(20160))
console.log(str.indexOf('?'))
console.log(str.lastIndexOf('?'))
console.log(str.indexOf('*'))
字符串大小写转换
**toLowerCase()**将字符串转换为小写字母 **toUpperCase()**将字符串转换为大写字母
var a='abc'
var b='edfg'
console.log(a.toUpperCase())
console.log(a.toUpperCase().toLocaleLowerCase())
字符串的拼接
***concat()**用于连接两个或多个字符串
var a='abc'
var b='edfg'
console.log(a.concat(b))
console.log(a.concat(b,'hao'))
字符串的截取
***split()**将字符串按照指定的字符分割为数组(字符串转换为数组)
***slice(start,end)**截取指定下标的字符串 slice(start)(第一个参数必填)从指定下标(start)开始截取,截取到最后 slice(start,end)从指定下标(start)开始截取,截取到指定结束下标(end)之前 注意: 1、在截取字符串时,包含起始下标(start),不包括结束下标(end) 2、截取的下标可以为负数,代表倒数第几个 3、slice截取为从左往右截取
***substr(start,num)**从起始索引(下标start)提取字符串中指定数目(num)的字符 start:起始下标(索引) 下标可以为负数,代表从倒数第几个开始 num:截取的字符串个数(截取的个数不能为负数)
**substring(start,stop)**提取字符串中两个指定的索引号之间的字符 注意:substring()功能基本和slice()一致,只是两个下标可以随意放置
ES6中的字符串函数使用 ***trim()**去除字符串两侧的空格
var str='什么?稻妻的雷神竟然有两个?'
console.log(str.split())
console.log(str.split(''))
console.log(str.slice(0,3))
console.log(str.substr(2,3))
var str='什么?稻妻的雷神竟然有两个?'
console.log(str.substring(0,2))
var str=" 没错,很有 可能 "
console.log(str.trim())
正则中的字符串查找匹配(正则表达式一起讲解)
search()
match()
replace()
7.7数学函数
数学函数的方法
abs()绝对值
max()最大值 注意:参数不能直接接收数组
min()最小值
*floor()向下取整(舍去所有的小数位)
ceil()向上取整(进一法取整)
round()四舍五入
*random()随机数
注意:默认产生0-1的随机数(可以取到0,但取不到1)
pow(x,y)次方根 返回x的y次幂
sqrt()开平方根
数学函数的属性
E 算数常量 代表e
PI 返回圆周率
console.log(Math.abs(-1))
console.log(Math.max(1,5,2,3))
console.log(Math.max(1,5,2,3))
var arr = [1,2,4,6,20,26];
var res = Math.max(arr)
console.log(res)
var res=Math.max.apply(Math,arr)
console.log(res)
console.log(Math.floor(9.9))
console.log(Math.ceil(9.1))
console.log(Math.round(9.1))
console.log(Math.round(9.5))
console.log(Math.pow(2,5))
console.log(Math.sqrt(9))
var num = Math.random();
console.log(num)
var num = Math.floor(Math.random()*10)
console.log(num)
var num = Math.floor(Math.random()*256)
console.log(num)
var arr = ['胡桃','行秋','七七','甘雨','魈','钟离','温蒂'];
var index = Math.floor(Math.random()*arr.length)
console.log(arr[index])
7.8时间函数
var date = new Date();
console.log(date)
// 查看对象原型内的方法
console.log(date.__proto__)
三种时间表现方式:
1、标准时间 toString()
2、国际时间 toLocaleString()
3、时间戳 valueOf()
在js中时间戳为14个数字(单位:毫秒)
时间戳返回的是当前时间距离1900年1月1日(时间纪元)零时的毫秒数
var date = new Date();
console.log(date.getFullYear())
console.log(date.getDate())
console.log(date.getYear())
console.log(date.toString())
console.log(date.toLocaleString())
console.log(date.valueOf())
GMT:格林威治时间(格林尼治或者天文学时间)
UTC:通用协调时
北京位于东八区 北京时间=UTC+8小时时差
7.9定时器
设置定时器
setTimeout(callback,时间)一次性定时器(只执行一次则结束)
callback代表回调函数 时间单位:毫秒
过多久时间执行一次函数体的内容
setTimeout(function(){
函数体
},1000)
setInterval(callback,时间)循环定时器(一直循环执行)
setInterval(function(){
函数体
},1000)
注意(方便理解):
for和setInterval的区别:
1、for在不满足判断条件会停止,setInterval若不进行手动清除,则不会停止
2、for不能控制每一次循环的时间,setInterval可以去控制每一次循环的时间
清除定时器
clearTimeout()清除一次性定时器
clearInterval()清除循环定时器
setTimeout(function(){
console.log(111)
},1000)
var time;
function start(){
time=setInterval(function(){
console.log(111)
},100)
}
function stop(){
clearInterval(time)
}
8.BOM
window对象
screen屏幕对象
location对象
history历史记录
navigator浏览器信息
window对象
在ES5中,最大的对象叫做Window,在ES6中,最大的对象为global
window的属性
screenLeft(screenX)获取浏览器左上角距离屏幕的X坐标
screenTop(screenY)获取浏览器左上角距离屏幕的Y坐标
innerWidth返回窗口的文档显示区的宽度(不包括任务栏和滚动条)
innerHeight返回窗口的文档显示区的高度
outerWidth返回窗口的宽度(包括任务栏和滚动条)
outerHeight返回窗口的高度
拓展:
offsetWidth获取指定对象的宽度
offsetHeight获取指定对象的高度
offsetLeft获取指定对象距离左侧的位置
offsetTop获取指定对象距离顶部的位置
scrollTop
opener返回对子窗口创建的引用(使用IE测试)
close返回窗口是否已关闭,返回Boolean 已关闭->true 未关闭->false
window的几种弹框方式
方式一:警告框
alert() 中断代码执行
方式二:显示带有一段消息以及确认按钮和取消按钮的对话框
confirm() 返回boolean值 确定->true 取消->false
方式三:输入弹框
prompt() 将输入框内输入的内容作为返回值返回
window的方法
open()打开一个新窗口或者已存在的窗口,返回一个window对象
moveTo()将窗口移动到指定的坐标
moveBy()将窗口按照指定的像素移动位置
resizeTo()将窗口大小调整到指定的宽度和高度
resizeBy()按照指定的宽度和高度调整窗口大小
scrollTo()将滚动条滚动到指定的像素
scrollBy()将滚动条按照指定的像素调整
close()关闭浏览器窗口
事件(重点)
onload监听页面加载
onunload监听页面退出(刷新 关闭页面)
onscroll监听页面滚动条滚动
location对象
host设置或返回主机名和端口号
hostname设置或返回主机名
port设置或返回端口号
protocol返回协议 比如:http https ftp
http状态码:https://www.runoob.com/http/http-status-codes.html
200 OK 请求成功
301永久移动
302临时移动
304 重定向 Not Modified
403服务器理解请求客户端的请求,但是拒绝执行此请求
404 not found 页面找不到
500 服务器错误
*href设置或返回完整的 URL (跳转会有历史记录)
pathname设置或返回URL的路径部分
拓展知识:
网址(域名) localhost http://www.jd.com:8080
公网ip地址 127.0.0.1
https和http的主要区别
HTTPS和HTTP的区别主要如下:
1、https协议需要到ca申请证书,一般免费证书较少,因而需要一定费用。
2、http是超文本传输协议,信息是明文传输,https则是具有安全性的ssl加密传输协议。
3、http和https使用的是完全不同的连接方式,用的端口也不一样,前者是80,后者是443。
4、http的连接很简单,是无状态的;HTTPS协议是由SSL+HTTP协议构建的可进行加密传输、身份认证的网络协议,比http协议安全
location的方法
assign()加载新文档
replace()加载新文档覆盖当前文档 无历史记录
reload()重新加载文档 F5 reload(true) ==ctrl+ F5 强制刷新
assign()和replace()的区别:
assign()加载文档会有历史记录
replace()加载没有历史记录
history对象
length返回浏览器历史列表中url的数量
forward()加载 history 列表中的后一个 URL
back()加载 history 列表中的前一个 URL
*go(n)加载 history 列表中的某个具体页面 n为数字,代表回到哪一个历史记录
注意:
go(-1)和back()效果一致
go(1)和forward()效果一致
9.DOM
DOM (document object model)文档对象模型,属于window,是window的子对象
9.1DOM简介
? W3C的标准,规定了如何通过Js创建web模型,可以通过js去操作页面的标签和样式,DOM既不属于html,也不属于javascript,是各大浏览器厂商指定一个页面执行标准
? 在HTML DOM标准中,所有的内容都是一个节点,所有节点的组合,我们叫做节点树
每一个标签是一个元素节点
每一个属性是一个属性节点
每一个文本是文本节点
每一个注释都是节点
整个html的document是一个文档节点
9.2常用结点
结点类型 | 节点标号 | 结点名 | 结点值 |
---|
元素结点 | 1 | 标签名(大写) | null | 属性结点 | 2 | 属性名 | 属性值 | 文本结点 | 3 | #text | 文本类型 | 文档结点 | 9 | #document | null |
结点特性:
nodeType:节点类型
nodeName:节点名
nodeValue:节点值
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title></title>
</head>
<body>
<h3 style="color: lightblue;" id="box">异世相遇,尽享美味</h3>
<script type="text/javascript">
var res=document.getElementById('box');
console.log(res.nodeType)
console.log(res.nodeName)
console.log(res.nodeValue)
var res=document.getElementById('box');
console.log(box.attributes)
var id=box.attributes[0];
console.log(id.nodeType)
console.log(id.nodeName)
console.log(id.nodeValue)
var res=document.getElementById('box');
var text=box.firstChild;
console.log(text.nodeType)
console.log(text.nodeName)
console.log(text.nodeValue)
console.log(document.nodeType);
console.log(document.nodeName);
console.log(document.nodeValue);
</script>
</body>
</html>
9.3结点访问
检测结点
childNodes 获取所有的子节点(以数组的方式返回) **hasChildNodes()**检测是否具有子节点(返回boolean值 true->具有子节点 false->没有子节点)
获取结点
firstChild查找第一个子节点 lastChild查找最后一个子节点 nextSibling查找下一个兄弟节点 previousSibling查找上一个兄弟节点 parentNode父节点
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title></title>
</head>
<body>
<ul id="box">
<li>望风山地</li>
<li>踏鞴砂</li>
<li>离岛</li>
<li>轻策庄</li>
</ul>
<script type="text/javascript">
var box =document.getElementById('box')
console.log(box.childNodes)
console.log(box.firstChild.nextSibling)
console.log(box.firstChild)
console.log(box.firstChild.nodeType)
box.firstChild.nodeType == 3?box.firstChild.nextSibling:box.firstChild;
console.log(box.firstChild)
console.log(box.lastChild)
console.log(box.lastChild.previousSibling)
box.lastChild.nodeType==3?box.lastChild.previousSibling:box.lastElementChild
console.log(box.parentNode)
console.log(box.parentNode.parentNode)
console.log(box.parentNode.parentNode.parentNode)
</script>
</body>
</html>
新的获取方式
新的获取方式:(高版本浏览器支持)
firstElementChild查找第一个元素子节点
lastElementChild查找最后一个元素子节点
nextElementSibling查找下一个元素节点
previousElementSibling查找上一个元素节点
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title></title>
</head>
<body>
<ul id="box">
<li>望风山地</li>
<li>踏鞴砂</li>
<li>离岛</li>
<li>轻策庄</li>
</ul>
<script type="text/javascript">
var box=document.querySelector('#box')
console.log(box.firstElementChild)
console.log(box.firstChild.nextSibling)
console.log(box.lastElementChild)
console.log(box.lastChild.previousSibling)
var oLi=document.querySelector('li')
console.log(oLi)
var oLi=document.querySelectorAll('li')
console.log(oLi)
</script>
</body>
</html>
克隆
克隆节点(复制) **cloneNode()**克隆节点 **cloneNode()**只克隆标签和属性 **cloneNode(true)**克隆标签+属性+文本 注意:若克隆的元素存在id属性,先修改其id的属性值,再添加到文档中
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title></title>
</head>
<body>
<div>
<p id="text">随便花</p>
</div>
<script type="text/javascript">
var text=document.getElementById('text')
var res=text.cloneNode()
console.log(res)
var res=text.cloneNode(true)
console.log(res)
var p=document.getElementsByTagName('p')[0]
p.appendChild(res)
</script>
</body>
</html>
9.4元素结点
创建,添加,移除,替换
创建元素:
createElement(标签名)创建元素节点
添加元素:
appendChild(元素节点)向指定节点追加一个子节点(默认放到所有子节点的末尾)
insertBefore(添加的元素,添加到指定元素之前)将元素添加到指定的节点之前
替换元素(修改元素)
replaceChild(替换后元素,替换前元素)替换元素节点
移除元素
removeChild(移除的元素)移除指定的子元素
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title></title>
</head>
<body>
<ul id="box">
<li>111111111</li>
<li>111111111</li>
<li>111111111</li>
<li>111111111</li>
</ul>
<script type="text/javascript">
var h2=document.createElement('h2')
h2.innerHTML='异世相遇'
console.log(h2)
var box=document.getElementById('box')
box.appendChild(h2)
</script>
</body>
</html>
var h2=document.createElement('h2')
h2.innerHTML='异世相遇'
console.log(h2)
var box=document.getElementById('box')
box.appendChild(h2)
var oLi=document.getElementsByTagName('li');
box.insertBefore(h2,oLi[1])
var input=document.createElement('input')
box.replaceChild(input,oLi[2])
box.removeChild(oLi[0])
元素节点获取
元素节点获取
获取单个元素:(直接返回元素节点)
getElementById()通过id名获取元素
querySelector()通过css选择符获取(必须高版本浏览器)
获取多个元素:(以数组的方式返回)
getElementsByClassName()通过class类名获取元素
getElementsByTagName()通过标签名获取元素
getElementsByName()通过name的值获取元素
querySelectorAll()通过css选择符获取所有
案例
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title></title>
<style type="text/css">
*{
padding: 0;
margin: 0;
}
#box{
width: 800px;
height: 400px;
background-color: aquamarine;
margin: 50px auto;
}
ul{
display: flex;
list-style: none;
font-size: 20px;
}
ul li{
width: 160px;
height: 50px;
text-align: center;
line-height: 50px;
background-color: lightseagreen;
border-bottom: 6px solid transparent;
}
ul li.active{
border-bottom: 6px solid red;
}
</style>
</head>
<body>
<div id="box">
<ul>
<li class="active">可莉</li>
<li>甘雨</li>
<li>胡桃</li>
<li>七七</li>
<li>优菈</li>
</ul>
</div>
<script type="text/javascript">
var arr =document.querySelectorAll('li');
for(var i=0;i<arr.length;i++){
arr[i].onclick=function(){
for(var j=0;j<arr.length;j++){
arr[j].style.borderBottom='6px solid transparent'
}
this.style.borderBottom='6px solid red'
}
}
</script>
</body>
</html>
9.5属性结点
attributes查看所有的属性节点 返回的值和数组类似,但不是真正的数组,他是所有属性的集合对象
?
获取指定的某个属性节点
- obj.attributes[i]
- obj.attributes.item(i)
?
重点:
**getAttribute(key)**获取指定属性结点的值 text
**setAttribute(key,val)**添加或修改指定属性节点
? 当属性名不存在时,则为添加属性节点
? 当属性名已存在时,则为修改属性节点
**removeAttribute(key)**移除指定的属性节点
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title></title>
</head>
<body>
<h2 style="color:red;"id="one">逃跑的太阳</h2>
<script type="text/javascript">
var one =document.getElementById('one');
console.log(one)
console.log(one.attributes)
console.log(one.attributes[0])
console.log(one.attributes.item(0))
console.log(one.getAttribute('id'))
one.setAttribute('name','可莉')
one.setAttribute('class','text1')
one.removeAttribute('style')
</script>
</body>
</html>
了解 :
createAttribute()创建属性节点
getNamedItem(key)获取指定的属性节点 id="text"
setNamedItem(attr)设置属性节点 (注意:设置之前必须先创建属性节点)
removeNamedItem(key)移除指定的属性节点
9.6文本结点
*innerHTML设置或获取位于对象起始和结束标签内的HTML (标签+文本)
outerHTML设置或获取对象及其内容的HTML形式(本身对象标签+标签+文本)
*innerText获取或者设置对象内的文本
outerText获取或者设置对象内的文本
*textContent获取或者设置对象内的文本
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title></title>
</head>
<body>
<p>异世相遇,尽享美味</p>
<div>
<a href="#">风龙废墟</a>
</div>
<script type="text/javascript">
var p=document.querySelector('p');
console.log(p)
var div=document.querySelector('div')
console.log(p.innerHTML)
console.log(div.innerHTML)
console.log(p.outerHTML)
console.log(div.outerHTML)
p.innerHTML='踏鞴砂'
console.log(div.innerText)
console.log(div.outerText)
console.log(div.textContent)
div.innerText='无想的一刀'
div.outerText='无想的一刀'
</script>
</body>
</html>
?
了解:文本结点的操作
appendData(txt) 向节点追加数据
insertData(start,txt) 向节点中插入数据
replaceData(start,num,txt) 替换节点数据
deleteData(start,num) 删除节点数据
substringData(start,num) 截取节点数据
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title></title>
</head>
<body>
<div>2.1版本还有一个月就要更新了</div>
<button type="button">appendData</button>
<button type="button">insertData</button>
<button type="button">replaceData</button>
<button type="button">deleteData</button>
<button type="button">substringData</button>
<script type="text/javascript">
var div=document.querySelector('div');
var text=div.firstChild
console.log(typeof div.innerHTML)
console.log(text.nodeName)
var btn=document.querySelectorAll('button')
btn[0].onclick=function(){
text.appendData('高兴')
}
btn[1].onclick=function(){
text.insertData(0,'原神')
}
btn[2].onclick=function(){
text.replaceData(0,3,'雷电将军')
}
btn[3].onclick=function(){
text.deleteData(0,3)
}
btn[4].onclick=function(){
var res=text.substringData(0,3)
console.log(res)
}
</script>
</body>
</html>
?
9.7文档结点
文档的属性:
body
title
cookie返回当前所有的cookie
文档的方法:
write()
writeln()
open()打开文档流
close()关闭文档流
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>genshin</title>
</head>
<body>
<script type="text/javascript">
console.log(document.title)
console.log(document.body)
console.log(document.domain)
console.log(document.lastModified)
document.writeln('文档流输出')
document.write('文档流输出')
</script>
</body>
</html>
9.8js操作css样式
obj.style.css属性
注意:
1、css属性若为border-radius等类型,需要驼峰命名法获取borderRadius
2、js中不能直接通过style获取内嵌式或者外部引入样式的css的属性值
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title></title>
</head>
<style>
.two{
width: 300px;
height: 300px;
}
</style>
<body>
<div style="width: 300px;height: 300px;background-color: plum;">
</div>
<div class="two">
</div>
<script src="getStyle.js" type="text/javascript" charset="utf-8"></script>
<script type="text/javascript">
var div=document.querySelector('div');
console.log(div.style.width)
console.log(div.style.height)
div.style.backgroundColor="red"
div.style.borderRadius="10px"
var two=document.querySelector('.two');
console.log(two.style.width)
var res=getStyle(two,'width');
console.log(res)
</script>
</body>
</html>
js无法获取css设置的内嵌或引用的样式,只能获取行内的。解决办法引入js函数:
function getStyle(obj,name){
if(window.getComputedStyle){
return getComputedStyle(obj,null)[name];
}else{
return obj.currentStyle[name];
}
}
10.事件
事件:元素在某种特定的情况下触发了javascript的函数。任何的元素都可以触发事件
10.1事件绑定
方式一:
<div onclick = "fun()"></div>
方式二:
box.onclick = function(){
console.log('绑定方式二')
}
取消事件绑定
box.onclick = null;
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title></title>
<style type="text/css">
div{
width: 300px;
height: 50px;
background-color: aquamarine;
margin: 2px auto;
text-align: center;
line-height: 50px;
}
</style>
</head>
<body>
<div onclick="mclick(e)">胡桃</div>
<div>甘雨</div>
<script type="text/javascript">
function mclick(){
console.log(1111)
}
var div=document.querySelectorAll('div')[1]
div.onclick=function(e){
var e=e || window.event
console.log(e)
console.log(222)
}
setTimeout(function(){
div.onclick=null
},2000)
</script>
</body>
</html>
10.2事件冒泡
? 当元素触发某个事件(比如onclick)后,向父级元素(从里往外)去不断的触发,直到最顶层位置,则为事件冒泡
? 普通浏览器到window为止 IE浏览器到document为止
? 但是部分事件没有事件冒泡:blur focus onload onunload…
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title></title>
<style type="text/css">
.outer{
width: 500px;
height: 500px;
background-color: pink;
margin: 0 auto;
}
.inner{
width: 200px;
height: 200px;
background-color: lightskyblue;
margin: 20px auto;
}
</style>
</head>
<body>
<div class="outer">
<div class="inner"></div>
</div>
<script type="text/javascript">
var outer=document.querySelector('.outer');
var inner=document.querySelector('.inner');
outer.onclick=function(){
console.log('outer!!')
}
inner.onclick=function(e){
console.log('inner!!')
var e=e || window.event;
e.stopPropagation ? e.stopPropagation() :e.cancelBubble=true;
}
</script>
</body>
</html>
10.3事件信息获取
事件内第一个参数一般设置为event 或者e等,该参数获取事件当前的信息
IE低版本只支持window.event
兼容性写法:var ev = e || window.event
获取事件触发的信息
currentTarget获取事件最顶层的触发元素
(当不存在事件冒泡时,currentTart和target的效果一致)
target获取当前触发该事件的元素
type返回当前事件类型
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title></title>
</head>
<body>
<button type="button">按钮</button>
<script type="text/javascript">
var btn =document.querySelector('button');
btn.onclick=function(){
var e= e || window.event;
console.log(e)
console.log(e.currentTarget)
console.log(e.target)
console.log(e.type)
}
</script>
</body>
</html>
10.4鼠标事件
onclick鼠标单击
ondblclick鼠标双击 click*2
onmousedown鼠标按键按下
onmouseup鼠标按键弹起
onmouseover鼠标移入 hover = onmouseover + onmouseout
onmouseout鼠标移出
onmousemove鼠标被移动
onmouseenter鼠标进入 (该事件不进行冒泡)
onmouseleave鼠标离开 (该事件不进行冒泡)
oncontextmenu当右键菜单展开触发
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title></title>
<style>
div{
width:300px;
height:50px;
background:lightblue;
margin:2px auto;
}
</style>
</head>
<body>
<div onclick="clickMe(this)">onclick</div>
<div ondblclick="clickMe(this)">ondblclick</div>
<div onmousedown="clickMe(this)">onmousedown</div>
<div onmouseup="clickMe(this)">onmouseup</div>
<div onmousemove="clickMe(this)">onmousemove</div>
<div onmouseover="clickMe(this)">onmouseover</div>
<div onmouseout="clickMe(this)">onmouseout</div>
<div onmouseenter="clickMe(this)">onmouseenter</div>
<div onmouseleave="clickMe(this)">onmouseleave</div>
<script>
function clickMe(obj){
obj.style.background = 'pink';
}
</script>
</body>
</html>
10.5阻止事件默认行为
阻止事件默认行为(常适用于具有默认行为的元素)
具有默认行为的元素:1、超链接 2、表单 3、右键菜单
preventDafult()适用于W3C标准的浏览器
returnValue=false IE阻止默认行为的方法
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title></title>
<style>
div{
width:100px;
height:300px;
background:lightblue;
display:none;
}
</style>
</head>
<body>
<div></div>
<a href="http://www.baidu.com">百度</a>
<script>
document.oncontextmenu = function(e){
var e = e || window.event;
e.preventDefault();
console.log(e)
e.preventDefault ? e.preventDefault() : e.returnValue = false;
var div = document.querySelector('div');
div.style.display = 'block'
console.log('右键菜单被打开')
}
var a = document.querySelector('a')
a.onclick = function(e){
var e = e || window.event;
e.preventDefault()
console.log('超链接被点击')
}
</script>
</body>
</html>
10.6键盘事件
onkeydown键盘按键按下
onkeyup键盘按键弹起
onkeypress键盘按键按下并弹起
10.7页面事件
onload 页面加载完成时执行
onunload 页面退出时执行
onresize 页面大小调整时执行
onscroll 页面滚动条滚动时执行
onmousewheel 鼠标滚动时执行(判断鼠标是上滑还是下滑)
window.onload=function(){
console.log('load..')
}
window.onunload=function(){
console.log('closed...')
}
window.onresize=function(){
console.log('窗口大小改变了...')
}
window.onscroll=function(){
console.log('scrolling...')
console.log(document.documentElement.scrollTop || document.body.scrollTop)
console.log(document.documentElement.scrollHeight)
}
10.8表单事件
onfocus 元素获得焦点
onblur 元素失去焦点
onchange 域的内容被改变(select下拉框)
onsubmit 确认按钮被点击(该事件绑定在form表单)
onreset 重置按钮被点击
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title></title>
<style type="text/css">
input{
border-radius: 10px;
}
.active{
border: 3px solid red;
outline: 0;
border-radius: 10px;
}
</style>
</head>
<body>
<form action="" method="" id="from">
姓名:<input type="text" id="user" /> <br>
密码:<input type="password" /><br>
<input type="submit" value="提交"/>
<input type="reset" value="重置"/>
<select name="character" id="character">
<option value="甘雨">甘雨</option>
<option value="七七">七七</option>
<option value="钟离">钟离</option>
<option value="胡桃">胡桃</option>
</select>
</form>
<script type="text/javascript">
var user=document.querySelector('#user');
user.onfocus=function(){
this.setAttribute('class','active')
}
user.onblur=function(){
this.removeAttribute('class')
console.log(this.value)
}
var character=document.querySelector('#character')
character.onchange=function(){
console.log(this.value)
}
character.onclick=function(){
console.log(11122333)
}
var from=document.querySelector('#from')
from.onsubmit=function(){
return true;
}
from.onreset=function(){
var res=confirm('确认要重置嘛?')
return res
}
</script>
</body>
</html>
10.9鼠标/键盘信息获取
button获取鼠标具体哪个按键按下
标准浏览器 0->左键 1->滚轮 2->右键
在IE中 1->左键 2->右键 4->滚轮 5->左键+滚轮 6->右键+滚轮 7->三者同时按下
keyCode 对于 keydown 事件,该属性声明了被敲击的键生成的 Unicode 字符码
左->37 上->38 右->39 下->40
which 返回键盘敲击按键生成的unicode编码
检测键盘是否按下特定的键,返回boolean (按下->true 没按下->false)
ctrlKey 检测键盘是否按下ctrl键
shiftKey 检测键盘是否按下shift键
altKey 检测键盘是否按下alt键
screenX 获取鼠标当前在屏幕上的X坐标
screenY 获取鼠标当前在屏幕上的Y坐标
clientX 获取鼠标当前在视窗上的X坐标
clientY 获取鼠标当前在视窗上的Y坐标
offsetX 获取鼠标当前距离操作元素的X坐标
offsetY 获取鼠标当前距离操作元素的Y坐标
移动小方块实例:
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title></title>
<style type="text/css">
.box{
width: 300px;
height: 300px;
background-color: lightskyblue;
left: 0px;
top: 0;
position: absolute;
}
</style>
</head>
<body>
<div class="box"></div>
<script src="getStyle.js" type="text/javascript" charset="utf-8"></script>
<script type="text/javascript">
var box =document.querySelector('.box');
box.onmousedown=function(e){
var e1=e || window.event;
document.onmousemove=function(e){
var e2=e || window.event;
console.log(e1.offsetX)
console.log(e2.clientX)
if(e2.clientX>=e1.offsetX && e2.clientX<=window.innerWidth-(getStyle(box,'width').slice(0,3)-e1.offsetX)){
var innerX=e2.clientX-e1.offsetX;
}
if(e2.clientY>e1.offsetY && e2.clientY<=window.innerHeight-(getStyle(box,'height').slice(0,3)-e1.offsetY)){
var innerY=e2.clientY-e1.offsetY;
}
box.style.left=innerX+'px'
box.style.top=innerY+'px'
}
}
document.onmouseup=function(){
document.onmousemove=null;
box.style.backgroundColor="hotpink";
}
</script>
</body>
</html>
10.10事件句柄
addEventListener(eventName,Listener,false)绑定事件 冒泡的方向(false true)
false->从里向外 true->从外往里
removeEventListener()移除事件
attachEvent(eventName,Listener)绑定事件(IE)
detachEvent()移除事件(IE)
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title></title>
<style type="text/css">
div{
width: 200px;
height: 200px;
background-color: lawngreen;
}
</style>
</head>
<body>
<div></div>
<script type="text/javascript">
var div=document.querySelector('div')
div.addEventListener('click',function(){
console.log(111)
})
div.addEventListener('click',function(){
console.log(222)
})
var listener1=function(){
console.log(333)
}
var listener2=function(){
console.log(444)
}
div.addEventListener('click',listener1,false)
div.addEventListener('click',listener2,false)
setTimeout(function(){
div.removeEventListener('click',listener1)
},2000)
</script>
</body>
</html>
兼容性封装方法:
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title></title>
<style type="text/css">
div{
width: 200px;
height: 200px;
background-color: lawngreen;
}
</style>
</head>
<body>
<div></div>
<script type="text/javascript">
var Listener={
add:function(obj,eventName,callback){
if(obj.addEventListener){
obj.addEventListener(eventName,callback,false)
}else{
obj.attachEvent('on'+eventName,callback)
}
},
remove:function(){
if(obj.removeEventListener){
obj.removeEventListener(eventName,callback)
}else{
obj.detachEvent('on'+eventName,callback)
}
}
}
var div=document.querySelector('div')
Listener.add(div,'click',function(){
console.log(111)
})
</script>
</body>
</html>
11.ES5中的this绑定
在ES5中this存在绑定问题(this的指代和其调用的位置有关),而ES6中无this的绑定(this只和其定义的位置有关,和调用的位置无关)
this的一个宗旨:this指代永远都是当前对象
11.1this在普通函数中被调用
var name='宵宫';
function fun(){
var name='早柚'
console.log(name)
console.log(this.name)
console.log(this==window)
console.log(this===window)
}
fun()
11.2this在对象内调用
方式一:this指代实例化对象
var obj={
name:'早柚',
age:20,
play:function(){
console.log(this==obj)
console.log(obj.name)
console.log(obj.age)
console.log(this.name)
console.log(this.age)
}
}
obj.play()
方式二:this作为实参传入
<button type="button" onclick="demo(this)">button</button>
function demo(obj){
console.log(obj)
obj.style.background='green'
}
方式三【重点】
li{
width: 200px;
height: 50px;
margin: 5px;
background-color: aqua;
}
<ul>
<li></li>
<li></li>
<li></li>
<li></li>
</ul>
var oLi=document.querySelectorAll('ul li')
for(var i=0;i<oLi.length;i++){
oLi[i].index=i;
oLi[i].onclick=function(){
console.log(this.index)
this.style.background='red'
}
}
方式四【易错点】
<h2>异世相遇,尽享美味</h2>
var h2=document.querySelector('h2')
h2.onclick=function(){
console.log(this)
var _this=this;
var that=this;
setTimeout(function(){
console.log(this)
_this.innerHTML='genshin impact'
},1000)
}
方式五:三和四的叠加使用
需要的功能效果:点击1s之后改变颜色
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title></title>
<style type="text/css">
li{
width: 200px;
height: 50px;
margin: 5px;
background-color: aqua;
}
</style>
</head>
<body>
<ul>
<li></li>
<li></li>
<li></li>
<li></li>
</ul>
<script type="text/javascript">
var oLi=document.querySelectorAll('ul li')
for(var i=0;i<oLi.length;i++){
oLi[i].index=i
oLi[i].onclick=function(){
console.log(this.index)
var that=this
setTimeout(function(){
oLi[that.index].style.background='red'
},1000)
}
}
</script>
</body>
</html>
11.3this在构造函数中使用
function test(name,age){
this.name=name;
this.age=age
this.play=function(){
console.log(this.name+'已经'+this.age+'岁了')
}
}
var dog=new test('poppy',1)
console.log(dog)
console.log(dog.name)
dog.play()
11.4this在apply(),call(),bind()中使用
var charactor={
name:'宵宫',
age:18,
play:function(a,b,c){
console.log(a,b,c,this.name+'是新的五星火系角色')
}
}
charactor.play()
var obj={
name:'迪奥娜',
age:'10',
say:function(){
console.log(this.name+'是一个很好用的辅助角色')
}
}
obj.say()
obj.say.apply()
obj.say.apply(charactor)
obj.say.call(charactor)
obj.say.bind(charactor)
var res=obj.say.bind(charactor)
console.log(res)
charactor.play.apply(obj,[1,2,3])
charactor.play.call(obj,1,2,3)
var res=charactor.play.bind(obj,1,2,3)
console.log(res)
res()
var arr=[1,2,5,6,4]
var max=Math.max(arr)
var max=Math.max.apply(Math,arr)
console.log(max)
apply、call、bind的区别
A.fun.apply(B,arr)将A对象切换为B对象,采用数组的方式传入参数
A.fun.call(B,arg1,arg2,arg3...)将A对象切换为B对象,需要一个一个单独传入参数
A.fun.bind(B,arg1,arg2,arg3...)将A对象切换为B对象,返回一个函数
12.缓存
12.1简介
缓存分类
- cookie
- session
- web Storage(localStorage sessionStorage)也叫做本地存储
12.2Cookie
cookie客户端缓存:
1、主要用于存储访问过的网站数据,存储浏览器的信息到本地计算机中,用于客户端和服务器端的通讯
注意:如果浏览器完全禁止cookie,大多数网站的基本功能都将无法正常使用,chrome浏览器不支持本地文件的cookie的读取
2、cookie的特点
- 以文本形式保存(.txt)
- cookie存储信息不安全(不能存放重要的信息)
- cookie中有域(domain)和路径的概念,浏览器是一个比较安全的环境,所以不同的域之间不能直接访问(js的同源策略限制)
协议 域名 端口全部一致才成为同一个域
http://localhost:3000
http://localhost/index:3000
4、cookie的常见信息
name cookie的名字(键)
value cookie存放的值
expires:指cookie过期的时间(该时间为世界时间 UTC时间)也成为格林威治时间
max-age:指cookie最大的存活有效期(单位:秒)
domain: 指的是cookie当前的域
path:指cookie当前的路径
size:指cookie存放的大小
secure:指cooke的安全属性
注意:expires和max-age的默认值为session
代表关闭浏览器,该cookie则清空、失效
5、cookie的设置和获取
function setCookie(name,value,minutes){
var now = new Date();
now.setMinutes(now.getMinutes()+minutes);
document.cookie = name+'='+value+';expires='+now.toUTCString();
}
将cookie的失效时间设置为过期时间,则cookie就清除了
setCookie('username',false,-1)
eg:
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title></title>
</head>
<body>
<script type="text/javascript">
var time=new Date();
time.setMinutes(time.getMinutes()+120)
console.log(time)
document.cookie='name=hutao;expires='+time.toUTCString()
document.cookie='username=ganyu;path=/;max-age=3600'
console.log(document.cookie)
function setCookie(name,value,minutes){
var time=new Date();
time.setMinutes(time.getMinutes()+minutes)
document.cookie=name+'='+value+';expires='+time.toUTCString();
}
setCookie('qiqi',123,60)
setTimeout(function(){
setCookie('qiqi',false,-1)
},5000)
setCookie('qiqi',false,-1)
</script>
</body>
</html>
12.3Session
session 服务器端缓存
变量保存的数据会保存在服务器端,通过返回一个session Id 来区分不同的用户。session Id会保存在本地的cookie
12.4Web Storage
localStorage和sessionStorage的区别:
localStorage:关闭浏览器数据仍然存在,除非手动清除
sessionStorage:仅存在于会话期间(关闭浏览器失效)
localStorage和sessionStorage的方法:
length属性 获取缓存的数量
getItem(key)获取缓存
setItem(key,val)设置或修改缓存
removeItem(key)移除缓存(删除单个缓存)
clear()清空所有的缓存
12.5缓存之间的联系
在html4中cookie在客户端保存用户名和简单的用户信息,cookie存在以下问题:
1、cookie的大小被限制在4Kb
2、占带宽:cookie是随着http一起被发送的,因此发送cookie则浪费带宽
3、操作cookie非常繁琐(需要我们去封装setCookie getCookie)
web Storage(本地存储)和cookie的异同:
共同点:都保存在本地浏览器中,和服务器端的session的机制不同
生命周期(缓存存活的最大时间):
- cookie:会设置一个expires(max-age)则cookie会在指定的时间失效,若没有设置结束时间,则默认为session,关闭浏览器则失效
- localStorage:关闭浏览器数据仍然存在,除非手动清除
- sessionStorage:仅存在于会话期间(关闭浏览器失效)
存储数据大小
- cookie的存储大小最多4Kb
- localStorage和seesionStorage一般可存储5M或者更大
服务器通讯
- cookie:对服务器发起http请求时,每次都会将数据携带在http请求中,过多保存cookie则带来性能问题
- localStorage和sessionStorage:数据不是由每个服务器请求传递,而是只有在请求时使用数据,而不参与服务器的通讯
13.对象的封装和继承
什么是js的封装?
我们需要将一些属性和方法隐藏起来,所以我们将这些属性和方法进行封装。然后通过外部的一个特定的接口(公有的方法)调用
涉及知识:
公有属性、公有方法、私有属性、私有方法
13.1对象的封装
封装的优点:
1、良好的封装可以减少耦合性(了解高内聚低耦合)
高内聚低耦合参考:https://blog.csdn.net/fangkang7/article/details/82684819
2、类的内部结构可以自由修改
3、可以对成员进行精确的控制
4、隐藏信息,实现细节
var person={
name:'宵宫',
age:16,
say:function(){
console.log(this.name+'今年'+this.age+'岁')
}
}
person.say()
console.log(person.name)
function Person(name,age,sex){
this.name=name;
this.age=age
var sex=sex
this.say=function(){
console.log('我的性别为:'+sex)
}
}
var people=new Person('早柚',18)
console.log(people)
var people=new Person('早柚',18,'女')
console.log(people)
people.say()
console.log(people.sex)
判断对象的所属关系
js中的安全模式:instanceof 判断是否由当前对象创建
instanceof判断结果为Boolean,属于则为true 不属于为false
13.2对象的继承
继承的意义:继承其实就是当多个方法存在相同的属性和方法时,就把这些相同的属性和方法提取到一个公共的方法中。
继承方式:
- 通过原型prototype继承
- 使用apply()、call()方法去继承
function Person(name,age,sex){
this.name=name;
this.age=age;
this.sex=sex;
this.show=function(){
console.log(name+'今年'+age+'岁了,是一个'+sex+'孩子!')
}
}
var sayu=new Person('早柚',16,'女')
console.log(sayu)
sayu.show()
function Student(score){
this.score=score
Person.call(this,name,age,sex)
}
var yoimia=new Person('宵宫',18,'女',90)
console.log(yoimia)
yoimia.show()
Teacher.prototype=new Person('优菈',20,'女');
function Teacher(type){
this.type=type
}
var teacher=new Teacher('教授')
console.log(teacher.name)
teacher.show()
13.3非对象的继承
浅拷贝:
var aa={
name:'胡桃',
city:['重庆','北京','上海']
}
var bb=aa
bb.nam='甘雨'
console.log(aa)
console.log(bb)
var obj={
name:'胡桃',
city:['重庆','北京','上海']
}
function copy(obj){
var newObj={}
for(var key in obj){
newObj[key]=obj[key]
}
return newObj
}
var newObj=copy(obj)
newObj.name='七七'
console.log(obj)
console.log(newObj)
深拷贝:
? 当复制的对象里面的属性含有引用类型时(object),浅拷贝复制之后,对原对象的引用类型的值进行改变时,新复制的对象的值也会跟着原对象而改变。
var obj={
name:'胡桃',
city:['重庆','北京','上海']
}
function deepcopy(obj,arr){
var newObj=arr||{}
for(var key in obj){
if(typeof obj[key] =="object"){
newObj[key]=obj[key].constructor == Array? []: {}
deepcopy(obj[key],newObj[key])
}else{
newObj[key]=obj[key]
}
}
return newObj
}
var newObj=deepcopy(obj)
newObj.name='七七'
obj.city.push('西藏')
console.log(obj)
console.log(newObj)
console.log(obj.city.constructor ==Array)
14.正则表达式
正则的作用:
*1、表单验证(检测用户名、密码等是否符合规范)
2、查找字符串
3、查找替换并替换
定界符
/正则规则/
原子
1、每一个字符都称为一个原子(数字、字母、下划线以及任何符号,包括空格)
2、每一个[]代表一个原子,中括号内为可选字符
[]号内的简写:
[0-9]代表0-9的任意一个数
[0-9A-Za-z_]代表数字、字母、下划线中的任意一个字符
注意:在[]内开头出现^,代表除了[]内以外的字符
3、{}代表重复匹配前面的原子
{m}重复匹配前面的原子m次
{m,n}重复匹配前面的原子至少m次,至多n次
{m,}重复匹配前面的原子至少m次
特殊的原子:
\d 代表0-9的任意一个数 相当于[0-9]
\D 代表除了0-9以外的任意字符 相当于[^0-9]
\w 代表数字、字母、下划线中的任意一个字符 相当于[0-9A-Za-z_]
\W 代表除了数字、字母、下划线以外的任意一个字符 相当于[^0-9A-Za-z_]
\s 代表所有的空白符(如:空格、换行、制表符)
\S 代表除了空白符以外的任意字符
元字符
. 代表任意一个字符
* 代表重复匹配前面的原子任意次 相当于{0,}
? 代表重复匹配前面的原子至少0次,至多1次 相当于{0,1}
+ 代表重复匹配前面的原子至少一次 相当于{1,}
模式修正符
i 不区分大小写
g 全局匹配
m 识别换行符
注意:模式修正符放置在定界符之外
定义正则表达式
// 方式一:通过定界符定义(推荐使用)
var pattern = /aaa/;
// 方式二:通过对象原型定义
var pattern = new RegExp('aaa');
严格模式
^必须以指定的字符开头 $必须以指定的字符结尾
必须完全符合正则表达式规则,才会验证通过
var pattern = /^[0-9A-Za-z_]{6}$/
贪婪模式
var pattern = /<li>.*<\/li>/;
var str = '<li>百事可乐</li><li>珍珠奶茶</li>';
var res = pattern.exec(str);
console.log(res)//<li>百事可乐</li><li>珍珠奶茶</li>
// 取消贪婪模式 .*?
var pattern = /<li>.*?<\/li>/;
var str = '<li>百事可乐</li><li>珍珠奶茶</li>';
var res = pattern.exec(str);
console.log(res)//<li>百事可乐</li>
正则的函数
exec()检测是否符合正则规则,将符合的部分以数组返回,不符合则返回null
语法:pattern.exec(str)
*test() 检测是否符合正则规范,返回Boolean值 符合->true 不符合->false
语法:pattern.test(str)
search()验证是否符合正则规则,返回字符第一次出现的下标
语法:str.search(pattern)
match()检测是否符合正则规范,将所有符合的内容全部以数组方式返回
(配合模式修正符g使用)
语法:str.match(pattern)
replace()将所有符合正则规则的内容进行替换
语法:str.replace(pattern,替换后的内容)
中文匹配
\u4e00-\u9fa5 中文的范围
var pattern = /[\u4e00-\u9fa5]/;代表任意的一个中文
|