<h1 style="width: 99px">dogFly</h1>
复制代码
<style>.fei{width: 99px;}</style>
复制代码
<link rel="stylesheet" href="./外联式.css">
复制代码
css外联样式的本质其实就是字符串替换 将下方这行代码替换成对应文件的全部代码javascript
<button onclick="window.alert('dogFly')">点靓仔</button>
复制代码
<script >alert("dogFly")</script >
复制代码
<script src="./外联式.js"></script>
复制代码
变量是计算机内存中存储数据的标识符,根据变量名称能够获取到内存中存储的数据css
有时候代码运行产生的数据咱们须要存储到内存中,方便之后使用前端
var age;
复制代码
age = 18;
复制代码
String()函数存在的意义:有些值没有toString(),这个时候可使用String(),好比:undefined和nulljava
如下八种状况会获得false,其他的一切数据获得都是true
数字0、-0、null、false、undefined、空字符串”“、NaN、document.allandroid
当运算符在运算时,若是两边数据不统一,CPU就没法计算,这时咱们编译器会自动将运算符两边的数据作一个数据类型转换,转成同样的数据类型再计算,这就是隐式转换ios
加+, 减-, 乘*, 除/, 模%算法
小于<, 小于等于<=, 大于>, 大于等于>=, 相等==, 不相等!=, 全等===, 不全等!==编程
与&&, 或||, 非!json
等于=,加等+=,减等-=,乘等*=,除等/=,模等%=api
++num, --num, num++, num--,
运算符的优先级不须要刻意的去记,由于开发中不多会遇到多个运算符参与的式子,万一遇到也能够经过()来提高优先级
js中算术运算符只能实现一些基本的数学计算,如加减乘除余等,若是想要实现更加高级的数学计算,如幂运算求平方根等则须要用到Math对象,Math对象的方法不少,不须要死记硬背,用到时查阅文档便可
运算符只是一种运算的符号,由运算符参与的式子称之为表达式
if (/* 条件表达式 */) {
// 执行语句
}
if (/* 条件表达式 */){
// 成立执行语句
} else {
// 不然执行语句
}
if (/* 条件1 */){
// 成立执行语句
} else if (/* 条件2 */){
// 成立执行语句
} else if (/* 条件3 */){
// 成立执行语句
} else {
// 最后默认执行语句
}
复制代码
表达式1 ? 表达式2 : 表达式3
复制代码
switch(表达式){
case 值1:
表达式的结果 === 值1,须要执行的代码
break;
case 值2:
表达式的结果 === 值2,须要执行的代码
break;
case 值3:
表达式的结果 === 值3,须要执行的代码
break;
.......
default:
表达式的结果和上面全部的case后面的值都不全等,则会执行这里的代码
break;
}
复制代码
<script>
/**合理穿透:当存在多种值须要执行相同代码时使用穿透能够节省代码
* 用户输入某一个月份,告诉用户这个月份属于什么季节
* 12,1,2 冬季
* 3,4,5 春季
* 6,7,8 夏季
* 9,10,11 秋季
*/
var month = +prompt("请输入月份");
switch (month){
case 12:
case 1:
case 2:
alert("冬季");
break;
case 3:
case 4:
case 5:
alert("春季");
break;
case 6:
case 7:
case 8:
alert("夏季");
break;
case 9:
case 10:
case 11:
alert("秋季");
break;
default:
alert("你输你🐎呢臭弟弟");
break;
}
</script>
复制代码
在javascript中,循环语句有三种,while、do..while、for循环
// for循环的表达式之间用的是;号分隔的,千万不要写成,
for (初始化表达式1; 判断表达式2; 自增表达式3) {
// 循环体4
}
复制代码
执行顺序:1243 ---- 243 -----243(直到循环条件变成false)
// 当循环条件为true时,执行循环体,
// 当循环条件为false时,结束循环。
while (循环条件) {
//循环体
}
复制代码
do..while循环和while循环很是像,两者常常能够相互替代,可是do..while的特色是无论条件成不成立,都会执行一次
do{
// 循环体;
} while (循环条件);
复制代码
break:当即跳出整个循环,即循环结束,开始执行循环后面的内容(直接跳到大括号)
continue:当即跳出当前循环,继续下一次循环(跳到i++的地方)
break既能够用于循环结构也能够用于switch分支结构,continue只能用于循环结构语句
<script>
//示例:吃包子:我买了十个包子,包子每次只能吃一个,须要循环吃十个
//break:假如吃到第五个我吃饱了,后面的包子就都不用吃了
//continue:假如吃到第五个吃出来小强,那我第五个不吃了,可是我没吃饱,后面仍是要继续吃
var sum = 0;
for(var i = 1;i<=10;i++){
//continue
// if(i == 5) {
// console.log ( "吃到小强了,这个包子我不吃了" );
// continue;//结束本次循环体(后面的代码不会执行),循环没有结束,仍是会依次执行语句3和语句2
// };
//break
if(i==5){
console.log ( "我吃饱了,后面的包子都不想吃了" );
break;//结束整个循环语句
}
console.log ( "我吃的是第" + i + "个包子" );
}
</script>
复制代码
<script>
/*1.逻辑运算符
* 逻辑与&&:一假则假
* 逻辑或||:一真则真
* 逻辑非!:取反
2.短路运算:
* 若是第一个式子就能够决定整个逻辑表达式的结果,那么第二个式子根本就不会去运行计算,这就叫短路运算
3.逻辑与表达式:
* 找假:若是第一个式子结果能转换为false,逻辑与表达式的结果就是第一个式子的值;不然就是第二个式子的值
4.逻辑或表达式:
* 找真:若是第一个式子结果能转换为true,逻辑或表达式的结果就是第一个式子的值;不然就是第二个式子的值
5.逻辑非表达式:
* 没有短路运算:由于它只有一个式子
*/
//1.若是第一个式子可以决定逻辑表达式的结果,那么第二个式子就不会执行:短路运算
// var num1 = 10;
// var num2 = 20;
// var res = num1 > 0 || ++num2;
// console.log ( res );//true
// console.log ( num2 );//20 此时右边式子没有执行
//2.逻辑运算符的结果不必定是true或者false,有多是其余的值
// var num1 = 10;
// var num2 = 20;
// var res = num1 || num2;
// console.log ( res );//10
//3.逻辑与表达式:&&
//找假:若是第一个式子结果能转换为false,逻辑与表达式的结果就是第一个式子的值;不然就是第二个式子的值
var num1 = 10;
var res1 = undefined && ++num1;
console.log ( res1 );//undefined
console.log ( num1 );//10 发生短路,第二个式子不会执行
//4.逻辑或表达式:||
//找真:若是第一个式子结果能转换为true,逻辑或表达式的结果就是第一个式子的值;不然就是第二个式子的值
var num2 = 20;
var res2 = 100 || ++num2;
console.log ( res2 );//100
console.log ( num2 );//20
</script>
复制代码
所谓数组,就是将多个元素(一般是同一类型)按必定顺序排列放到一个集合中,那么这个集合咱们就称之为数组
数组是一个有序的列表,能够在数组中存听任意的数据,而且数组的长度能够动态的调整
var arr = [50,88,25,60,45];
//1.求数组中全部元素的平均值
var sum = 0;
for(var i = 0;i<arr.length;i++){
sum += arr[i];
}
console.log ( sum / arr.length );//平均数
//2.求数组中元素最大值
//打擂台思想
var max = - Infinity;
for(var i = 0;i<arr.length;i++){
if(max <= arr[i]){
max = arr[i];
}
}
console.log ( max );
//3.求数组中元素最小值
var min = Infinity;
for(var i = 0;i<arr.length;i++){
if(min >= arr[i]){
min = arr[i];
}
}
console.log ( min );
复制代码
//翻转数组
var arr = [90,88,20,100,5];//翻转以后:[5,100,20,88,90]
// console.log ( arr );
//1.倒着对数组遍历
var newArr = [];
for(var i = arr.length - 1;i>=0;i--){
console.log ( arr[ i ] );
//2.将倒着遍历的元素按照顺序添加到新数组中
newArr[newArr.length] = arr[i];
}
console.log ( newArr );
//1.2 将数组首尾元素的值互换
for(var i = 0;i<arr.length/2;i++){
console.log ( arr[ i ] );
//交换首尾元素的位置
//交换arr[i]和arr[arr.leth-1 - i]这两个元素的值
var temp = arr[i];
arr[i] = arr[arr.length-1 - i];
arr[arr.length-1 - i] = temp;
}
console.log ( arr );
复制代码
<script>
/**
* 开关比较法
* 1.先定义个空的新数组newArr
* 2.遍历旧数组arr中全部元素
* 3.定义一个bollean变量表示开关,默认为开启状态
* 4.遍历新数组全部元素与旧数组元素比较
* 5.若是该元素存在于新数组中,开关为关闭状态。不然开关为开启状态
* 6.若是开关为开启状态,则将旧数组的元素添加到新数组中
*/
var arr = [20,25,66,78,25,66,39];//[20,25,66,78,39]
//1.定义个空的新数组
var newArr = [];
//2.遍历旧数组中全部元素
for(var i = 0;i<arr.length;i++){
//3.定义一个开关,默认为开启状态
var canAdd = true;
//4.遍历新数组全部元素
for(var j = 0;j<newArr.length;j++){
if(newArr[j] === arr[i]){
//5.若是存在,开关关闭
canAdd = false;
break;//一旦重复,后面不必比较,结束本次循环
};
//5.不存在,开关继续保持开启状态
}
//6.若是开关为开启状态,则将旧数组的元素添加到新数组中
if(canAdd == true){
newArr[newArr.length] = arr[i];//往新数组后面添加元素
}
}
console.log ( newArr );
</script>
复制代码
//斐波那契阿数列:1,1,2,3,5,8,13,21,34,55..... 求第十位数字是几?
//特色:从第三个数字开始,每个数字是前两个数字的和
var fibNum = [1,1];
for(var i = 2;i<10;i++){//i=2 是由于从下标为2的数字开始 才是 前面两个元素的和
fibNum[i] = fibNum[i-1] + fibNum[i-2];
};
console.log ( fibNum );
console.log ( fibNum[ fibNum.length - 1 ] );//数组中最后一个元素
复制代码
冒泡算法排序核心:数组中相邻的两个元素比较大小,若是前者大于后者则交换位置
每一轮比较能够找出数组中最大的那个数字,而且移到了数组的最后面
<script>
/*排序:将数组中的元素按照从小到大的顺序排列
冒泡法排序核心原理:数组中相邻的两个元素比较大小,若是前者大于后者则交换位置
* 每一轮比较能够找出数组中最大的那个数字
*/
var arr = [18,15,10,20,5];//[5,10,15,18,20]
//1.获取数组中全部元素:数组遍历
for(var i = 0;i<arr.length-1;i++) {//i = 0 1 2 3
//2.让相邻的两个元素比较大小,若是前者大于后者就交换位置
//本身:arr[i] 相邻的那个元素:arr[i+1]
console.log ( "第" + i + "次" + arr[ i ] + "和" + arr[ i + 1 ] + "比较" );//
if ( arr[ i ] > arr[ i + 1 ] ) {
//3.交换位置:交换两个变量的值
var temp = arr[ i ];
arr[ i ] = arr[ i + 1 ];
arr[ i + 1 ] = temp;
}
console.log ( "第" + i + "次比较以后,数组变成了" + arr );//
}
console.log ( "第一轮比较的结果是" + arr );
//总结规律:循环会执行五次 [18,15,10,20,5]
//第一次 18 > 15 交换位置 [15,18,10,20,5]
//第二次 18 > 10 交换位置 [15,10,18,20,5]
//第三次 18 < 20 位置不变 [15,10,18,20,5]
//第四次 20 > 5 交换位置 [15,10,18,5,20]
//第五次比较 20 和undefined比较 无心思 [15,10,18,5,20] 最后一次比较无心义的,五个数字只须要比较四次就能够了
//本次循环结束以后,最大的那个数字会变成数组的最后一个元素(一轮比较只能找出数组中最大的那个数字)
//第二轮:再来一轮:能够找出第二大的数字 [15,10,18,5,20]
for(var i = 0;i<arr.length - 1;i++) {//i = 0 1 2 3
//2.让相邻的两个元素比较大小,若是前者大于后者就交换位置
//本身:arr[i] 相邻的那个元素:arr[i+1]
console.log ( "第" + i + "次" + arr[ i ] + "和" + arr[ i + 1 ] + "比较" );//
if ( arr[ i ] > arr[ i + 1 ] ) {
//3.交换位置:交换两个变量的值
var temp = arr[ i ];
arr[ i ] = arr[ i + 1 ];
arr[ i + 1 ] = temp;
}
console.log ( "第" + i + "次比较以后,数组变成了" + arr );//
}
console.log ( "第二轮比较的结果是" + arr );
/**第二轮比较过程:找出第二大的数字
* 第一次 15 > 10 交换位置 [10,15,18,5,20]
* 第二次 15<18 位置不换 [10,15,18,5,20]
* 第三次 18>5 交换位置 10,15,5,18,20]
* 第四次: 18 < 20 由于此时数组的最后一个元素已是最大的了,本轮找出的最大数组只能是数组的倒数第二个
*/
//第三轮:再来一轮:能够找出第三大的数字 [10,15,5,18,20]
for(var i = 0;i<arr.length - 1;i++) {//i = 0 1 2 3
//2.让相邻的两个元素比较大小,若是前者大于后者就交换位置
//本身:arr[i] 相邻的那个元素:arr[i+1]
console.log ( "第" + i + "次" + arr[ i ] + "和" + arr[ i + 1 ] + "比较" );//
if ( arr[ i ] > arr[ i + 1 ] ) {
//3.交换位置:交换两个变量的值
var temp = arr[ i ];
arr[ i ] = arr[ i + 1 ];
arr[ i + 1 ] = temp;
}
console.log ( "第" + i + "次比较以后,数组变成了" + arr );//
}
console.log ( "第三轮比较的结果是" + arr );
//第四轮:再来一轮:能够找出第四大的数字 [10,15,5,18,20]
for(var i = 0;i<arr.length - 1;i++) {//i = 0 1 2 3
//2.让相邻的两个元素比较大小,若是前者大于后者就交换位置
//本身:arr[i] 相邻的那个元素:arr[i+1]
console.log ( "第" + i + "次" + arr[ i ] + "和" + arr[ i + 1 ] + "比较" );//
if ( arr[ i ] > arr[ i + 1 ] ) {
//3.交换位置:交换两个变量的值
var temp = arr[ i ];
arr[ i ] = arr[ i + 1 ];
arr[ i + 1 ] = temp;
}
console.log ( "第" + i + "次比较以后,数组变成了" + arr );//
}
console.log ( "第四轮比较的结果是" + arr );
//第四轮结束以后,因为数组只有五个元素,已经找出了前面四个最大的元素,剩下的这一个元素一定是最小的
//没有必要比较
</script>
复制代码
for(var i = 0;i<arr.length - 1;i++){//1.外层循环决定比较的轮数
for(var j = 0;j< arr.length - 1 - i;j++){//2.内层循环决定每一轮比较的次数
if(arr[j] > arr[j+1]){//3.交换相邻元素:比较两个相邻数字的大小
var temp = arr[j];
arr[j] = arr[j+1];
arr[j+1] = temp;
}
}
}
复制代码
<script>
//分析i和j的由来
var arr = [18,15,10,20,5];
/*找规律:第一个规律:找出须要比较的轮数
1.数组的长度为5 须要比较4轮
2.数组的长度为6,须要比较5轮
3.数组的长度为 arr.length 须要比较 arr.lenthg - 1 轮
第二个规律:找出每一轮须要比较多少次
数组长度为5 第一轮 i = 0 :须要比较四次
数组长度为5 第二轮 i =1: 须要比较三次 (由于第一轮已经找出了最大的数放在数组的最后面)
数组长度为5 第三轮 i = 2:须要比较两次 (由于前两轮已经找出了最大的两个数字,本轮只须要比较前面三个数字便可)
数组长度为5 第四轮 i = 3:须要比较1次 (由于前三轮已经找出了最大的三个数字,本轮只须要比较前面两个数字大小便可)
arr.length - i的值 -1 = 每一轮须要比较的次数
*/
//1.外层循环决定行:轮数
for(var i = 0;i<arr.length - 1;i++){
//当i = 0 的时候(第一轮) 比较4次 4 + 0 = 4
//当i = 1的时候(第二轮) 比较 3 次 3 + 1 = 4
//当i = 2的时候(第三轮) 比较 2 次 2 + 2 = 4
//当i = 3的时候(第四轮) 比较 1 次 3 + 1 = 4
//规律:每一轮须要比较的次数 + i = arr.length - 1 (将i挪到等式右边求出每轮比较次数)
//每一轮须要比较的次数 = arr.length - 1 - i
//内层循环决定每一轮比较的次数
for(var j = 0;j< arr.length - 1 - i;j++){
//比较两个相邻数字的大小
if(arr[j] > arr[j+1]){
var temp = arr[j];
arr[j] = arr[j+1];
arr[j+1] = temp;
}
}
}
console.log ( arr );//
</script>
复制代码
引用类型:array,obejct 数据存储在堆中,地址存储在栈中
值类型:string number boolean undefined null 数据存储在栈中
区别:
值类型:栈中存储的是数据,变量赋值时拷贝的是数据,修改拷贝后的数据不会对原数据形成影响
引用类型:栈中存储的是地址,变量赋值时拷贝的也是地址,修改拷贝后的数据会对原数据形成影响
把一段相对独立的具备特定功能的代码块封装起来,造成一个独立实体,就是函数,起个名字(函数名),在后续开发中能够反复调用
函数的做用就是封装一段代码,未来能够重复使用
function 函数名(){
// 函数体
}
复制代码
var 函数名 = function() {
// 函数体
}
复制代码
函数声明能够在任何地方调用,而函数表达式方式调用必须在声明后面
<script>
//函数有两种声明方式
//1.函数声明: function 函数名() {};
function fn1 ( ) {
console.log ( "哈哈" );
}
//2.函数表达式: var 函数名 = 匿名函数
var fn2 = function ( ) {
console.log ( "呵呵" );
}
//这两种方式惟一的区别:函数声明能够在任何地方调用,而函数表达式方式调用必须在声明后面
// test();//这样调用会报错
var test = function ( ) {
console.log ( "嘿嘿" );
}
test();//只能在声明的后面调用
</script>
复制代码
函数内部是一个封闭的环境,能够经过参数的方式,把外部的值传递给函数内部
形式参数:在声明一个函数的时候,为了函数的功能更加灵活,有些值是固定不了的,对于这些固定不了的值。咱们能够给函数设置参数。这个参数没有具体的值,仅仅起到一个占位置的做用,咱们一般称之为形式参数,也叫形参
实际参数:若是函数在声明时,设置了形参,那么在函数调用的时候就须要传入对应的参数,咱们把传入的参数叫作实际参数,也叫实参
就是实参给形参赋值
<script>
//return关键字:结束函数的调用 (相似于break关键字,只能用于函数体中)
//return后面的代码不会执行
//写一个函数:判断一个数是否是偶数
function isOuShu ( num ) {
if(num %2 == 0){
console.log ( num + "是偶数" );
return;
}
console.log ( num + "不是偶数" );
}
isOuShu(1);
isOuShu(2);
</script>
复制代码
当函数执行完的时候,并非全部时候都要把结果打印。咱们指望函数给我一些反馈(好比计算的结果返回进行后续的运算),这个时候可让函数返回一些东西,也就是返回值
函数经过return返回一个返回值
//声明一个带返回值的函数
function 函数名(形参1, 形参2, 形参...){
//函数体
return 返回值;
}
//能够经过变量来接收这个返回值
var 变量 = 函数名(实参1, 实参2, 实参3);
复制代码
当前函数的内置对象,每个函数都有一个arguments对象,做用是存储调用者传递过来的全部实参
js是一门弱语言,声明函数的时候假如只有一个形参,实际上在调用的时候不管咱们传入多少实参程序都不会报错,为了防止这种状况,就用arguments关键字来获取全部的实参
<script>
/**arguments关键字做用:获取函数的全部实参
* 本质:当前函数的内置对象,每个函数都有一个arguments对象,做用是存储调用者传递过来的全部实参
* 特色:1.只能在函数体中使用,函数外部使用会报错
* 2.是一个特殊的数组(伪数组)
* 3.arguments伪数组的元素与形参一一对应
*
* 说明:1.能够用函数变得更加灵活
* 2.arguments是一个伪数组
* * 伪数组:只有数组的下标、元素、长度,没有数组其余方法
*/
/**一:argument用法演示*/
//1.这行代码会报错,由于函数外部没法使用arguments
// console.log ( arguments );
//2.定义一个无参的函数,做用是打印该函数的全部参数
function fn ( num1 ) {
//(1)arguemnt保存的是全部的实参的值
// console.log ( num1 );
// console.log ( arguments );//arguments只能在函数内部使用
//(2)arguemnt与形参是一一对应的
//修改了形参,arguemnt也会修改
num1 = 100;
console.log ( arguments );//修改了形参,arguments也会修改
//反之,修改了argeumnts,形参也会变化
}
fn(10,20);//实参与形参一一对应
/** 二:arguments实际用途展现:根据参数的数量让函数实现不一样的功能 */
function test ( ) {
if(arguments.length == 0){
//执行这个代码
console.log ( "没有参数" );
}else if(arguments.length == 1){
//执行这个代码
console.log ( arguments[ 1 ] );
}else{
//执行这个代码
console.log ( arguments[ 0 ] + arguments[ 1 ] );
}
}
test();
test(100);
test(10,20);
</script>
复制代码
通常的开发者工具都会自动帮你生成函数的注释,只须要在函数声明的上方输入/** + 回车,它会本身帮你生成一堆东西(函数的做用、每个参数的意思、返回值的意思),这就是函数的标准注释,以下所示
/**
* 求数组中的最大数
* @param arr:数组
* @return max:最大数
*/
function getMaxNumber ( arr ) {
var max = -Infinity;
for(var i = 0;i<arr.length;i++){
if(max <= arr[i]){
max = arr[i];
}
}
return max;
}
复制代码
回调函数:若是一个函数的参数也是一个函数,那么这个参数函数就叫作回调函数
当一个函数调用执行完毕以后,我想执行另外一段代码块,也就是调用另外一个函数
可是有时候可能本函数执行完毕后,根据不一样的状况须要调用的函数也不一样,那么咱们可使用形参来接收这个函数,而后再调用
此时:这个形参函数就称之为回调函数
<script>
//回调函数:若是一个函数的参数也是一个函数,那么这个参数函数就叫作回调函数
//回调函数在什么地方会执行呢? 函数名() 的时候执行
//回调函数难点: 本质是一个参数
//谁来传:调用者传参 (函数名)
//谁来收,调用:函数调用 (函数执行完函数体以后,调用保存在这个参数中的一段代码)
function a ( ) {
console.log ( "哈哈" );
}
function b ( ) {
console.log ( "呵呵" );
}
//c函数有一个功能,能够接收调用者传递过来的一段代码,而且在执行完自身函数体以后,会帮调用者执行这一段代码
function c ( fn ) {
console.log ( "嘿嘿" );
//fn里面是调用者传递过来的一段代码,怎么让这段代码执行呢?
fn();
};
//调用函数c,传的是变量a中存储的一段代码
c(a);
c(b);
</script>
复制代码
匿名函数:没有名字的函数
自调用函数:函数本身调用本身
最多见的:匿名函数自调用
开辟做用域,js中只有函数才能够开辟做用域
防止全局变量污染
将整个函数使用小括号包裹,而后在后面再加上小括号调用
<script>
/*自调用函数:函数本身调用本身
* 最多见的:匿名函数自调用
*/
//做用:开辟做用域,js中只有函数才能够开辟做用域
//匿名函数至关于字面量函数,因为没有函数名,因此只能在声明的同时调用
//语法: ( function(){} ) () 将整个函数使用小括号包裹,而后在后面再加上小括号调用
(function ( ) {
console.log ( "我是匿名函数" );
})();
//补充:其实有名字的函数也能够本身调用本身,只是比较少见
(function test( ) {
console.log ( "我是有名字的函数,我也能够自调用" );
})();
</script>
复制代码
<script>
/*做用域:变量起做用的范围
* js中只有两种:全局做用域 局部做用域
*
1.全局做用域:变量在任何地方起做用
* 全局变量:在函数外面声明
2.局部做用域:变量只能在函数内部起做用
* 局部变量:在函数内部声明
*/
//1.全局变量
var a = 10;
function fn ( ) {
console.log ( a );
}
fn();
//2.局部变量
function fn1 ( ) {
var num = 10;
console.log ( num );
}
fn1();
console.log ( num );
//不使用var声明的变量是全局变量,不推荐使用
</script>
复制代码
只有函数能够制造做用域结构,那么只要是代码,就至少有一个做用域,即全局做用域。
凡是代码中有函数,那么这个函数就构成另外一个做用域。
若是函数中还有函数,那么在这个做用域中就又能够诞生一个做用域。
将这样的全部的做用域列出来,能够有一个结构: 函数内指向函数外的链式结构。就称做做用域链。
就近原则:访问变量时,会优先访问的是在本身做用域链上声明的变量,若是本身做用域链上没有声明这个变量,那么就往上一级去找有没有声明这个变量,若是有就访问,若是没有就继续往上找有没有声明,直到找到0级做用域链上,若是有,就访问,若是没有就报错
JavaScript代码的执行是由浏览器中的JavaScript解析器来执行的。
JavaScript解析器执行JavaScript代码的时候,分为两个过程:预解析过程和代码执行过程
var a = 25;
function abc (){
alert(a);//undefined
var a = 10;
}
abc();
// 若是变量和函数同名的话,函数优先
console.log(a);
function a() {
console.log('aaaaa');
}
var a = 1;
console.log(a);
复制代码
####对象概念
<script>
/**
* 1.对象类型:能够理解为使用js代码来描述生活中的某个具体的事物
* 2.例如 人有哪些特征与行为呢
* 特征:姓名,年龄
* 行为:吃饭,睡觉
* 3.对象的属性:用于描述对象的特征
* 4.对象的方法:用于描述对象的行为
*/
var name = 'dogFly';
var age = 99;
var sex = '男';
//需求:使用一个变量来存储一我的的信息
//使用数组,易读性不高,根本不知道每个下标表示的是什么数据
//解决方案:使用对象,既能够存储多个数据,也能够提升代码易读性
var arr = [];
arr[0] = 'dogFly';
arr[1] = 99;
arr[2] = '男';
console.log ( arr );
//1.声明一个对象: 语法 var 对象名 = new Object()
var gouFei = new Object();//建立一个空对象
gouFei.name = 'dogFly';
gouFei.sex = '男';
gouFei.age = 99;
console.log ( gouFei );
//2.对象经过属性来取值 点语法 对象名.属性名
console.log ( gouFei.name );
//补充:对象与数组之间的异同点
/*相同点:均可以存储多个数据
不一样点:数组是按照顺序来存储的,对象是无序存储的
*/
//对象:使用代码来描述现实世界的事物
/*现实世界中的人
* 属性:年龄 身高 性别
* 行为(函数):吃饭 睡觉
*
汽车:
* 属性(特征):颜色 轮子 价格
* 行为:飙车 刹车
*/
</script>
复制代码
####对象的使用
<script>
/*本小节知识点:对象的取值与赋值
取值:两种语法
* 点语法: 对象名.属性名
* 字符串语法 对象名['属性名']
赋值: 取值 = 要赋的值
* 对象名.属性名 = 属性的值
* 对象名['属性名'] = 属性的值
*/
//1.声明一个对象
//new Object() :构造函数方式 :若是调用一个函数使用了new关键字,那么这个函数就称为构造函数
//构造函数会自动返回一个对象
var person = new Object();
console.log ( person );
//2.赋值语法: 对象名.属性 = 值
//2.1 若是对象没有这个属性,则是动态添加这个属性
person.name = 'dogFly';
person.age = 66;
console.log ( person);
//2.2 若是有这个属性,则是修改属性值
person.name = 'coolFly';
console.log ( person );
//3.取值语法:两种取值语法
//(1)点语法: 对象名.属性名 (2字符串语法: 对象名['属性名']
//3.1 点语法 对象名.属性名
console.log ( person.age );//38
//3.2 若是没有这个属性,则取到的是undefined
console.log ( person.xxxxxx );
//3.3 字符串语法
console.log ( person[ "age" ] );
//4.练习题
var zhangsan = new Object();
zhangsan.name = '张三';
zhangsan.age = 18;
var name = 'age';
console.log ( zhangsan[ name ] );//18 zhangssan['age''] </script> 复制代码
什么是对象的初始化:在声明对象的同时赋值
初始化:开辟内存空间的同时存储数据
<script>
/*对象描述现实世界的事物,人
特性(属性):姓名,年龄,性别
行为: 吃饭 睡觉 大宝剑
*/
//对象的初始化
var person = new Object({
//语法: 属性名 : 属性值 (键值对)
name : 'dogFly',
age : 99,
sex : '男',
sayHi:function(){
console.log ( "你好,我是狗飞" );
},
girlFirend : {
name : 'gakki',
age : 18,
play : function(){
console.log ( "来过来抱抱" );
}
}
});
//取值
console.log ( person.name );
person.sayHi();//调用对象的方法
console.log ( person.girlFirend );//这个属性是个对象
console.log ( person.girlFirend.name );
person.girlFirend.play();
//赋值
person.girlFirend.name = '20岁のgakki';
console.log ( person.girlFirend );
//若是对象的属性是一个函数,咱们就称这个函数叫作方法。 方法有归属感
</script>
复制代码
var o = {
name: 'zs',
age: 18,
sex: true,
sayHi: function () {
console.log(this.name);
}
};
复制代码
var person = new Object();
person.name = 'lisi';
person.age = 35;
person.job = 'actor';
person.sayHi = function(){
console.log('Hello,everyBody');
}
复制代码
function createPerson(name, age, job) {
var person = new Object();
person.name = name;
person.age = age;
person.job = job;
person.sayHi = function(){
console.log('Hello,everyBody');
}
return person;
}
var p1 = createPerson('张三', 22, 'actor');
复制代码
for(var 属性名 in 对象名){
//这里只能使用字符串语法取值,由于获取的属性名是一个字符串
var 属性的值 = 对象名[属性名]
}
复制代码
function fun() {
this.name = 'mm';
}
var obj = new fun();
console.log(obj.name); // mm
delete obj.name;
console.log(obj.name); // undefined
复制代码
方法:其实就是一个函数,只不过它是对象的一个属性,因此咱们称之为方法
this关键字:谁调用这个方法,this就表明谁
JavaScript中的this指向问题,有时候会让人难以捉摸,随着学习的深刻,咱们能够逐渐了解 如今咱们须要掌握函数内部的this几个特色
<script>
//方法中this表明谁? : 谁调用这个方法,this就表明谁
var person = {
name : 'dogFly',
age : 99,
sayHi : function ( ) {
//1.能够在对象的方法中获取对象的属性
console.log ( "个人名字是" + person.name + "个人年龄是" + person.age );
//2.this关键字获取对象
console.log ( "个人名字是" + this.name + "个人年龄是" + this.age );
}
}
//person这个对象调用了它的方法,this就表明person这个对象
person.sayHi();
person.name = 'gakki';//修改对象的属性,this也会跟着改变(动态指向)
person.sayHi();
</script>
复制代码
构造函数 ,是一种特殊的函数。
主要用来在建立对象时初始化对象, 即为对象成员变量赋初始值,总与new运算符一块儿使用在建立对象的语句中。
若是调用一个函数的时候使用了new关键字,那么这个函数就是构造函数
<script>
//自定义构造函数
//什么是构造函数:若是调用一个函数的时候加了new关键字,那么这个函数咱们称之为构造函数
//1.声明一个空函数
function fn ( ) {
}
//查看使用new调用和不使用new调用的结果有什么不一样
var res1 = fn();//不加new关键字,此时fn就是普通函数
var res2 = new fn();//加new关键字,fn就变成了构造函数
console.log ( res1 );//undefined
console.log ( res2 ,typeof res2);//object 空对象(对象名就叫作fn)
//结论:使用new关键字以后,函数在内部会自动建立一个对象,而且帮咱们自动返回
//2.既然构造函数内部会自动建立一个对象,那么可使用this关键字来表明这个对象
function Teacher ( name,age,hobby ) {
this.name = name;
this.age = age;
this.hobby = hobby;
}
//使用new关键字调用构造函数
var teacher2 = new Teacher ( "琨琨", 5, "篮球" );
console.log ( teacher2 );//{name: "琨琨", age: 5, hobby: "篮球"}
/*new这个关键字在构造函数中会作四件事
* 1.在内存中开辟空间,建立一个空对象
* 2.把this指向这个对象
* 3.给这个对象赋值
* 4.将这个对象返回(return)
*/
//3.构造函数使用注意点
/*1.一般函数名首字母大写,用于区分普通函数
2.必需要使用new关键字来调用
3.手动在函数内return形成的影响
* 若是 return 基本数据类型 : 无效,仍是会返回默认对象
* 若是 return 复杂数据类型 : 有效,会覆盖默认的对象
*/
function GirlFirend(name,age){
this.name = name;
this.age = age;
//若是手动return
// return '123' ; //基本数据类型,无效
//return ['123']; //复杂数据类型,有效,会覆盖默认对象
}
var person1 = new GirlFirend('gakki',18);
console.log ( person1 );
</script>
复制代码
经过目前的学习,咱们对js的对象有了必定的了解,其实在js中还有一些内置对象
内置对象:js的做者提早写好的对象
做用:将一些数据类型经常使用的属性或者方法提早写好,减轻开发者的工做量
API:(Application ProgrammingInterface,应用程序编程接口)是一些预先定义的函数,目的是提供应用程序与开发人员基于某软件或硬件得以访问一组例程的能力,而又无需访问源码,或理解内部工做机制的细节
内置对象的方法不少,不须要刻意的死记硬背,熟能生巧
<script>
/**
* Date对象:js内置的用于获取当前日期与时间的对象
* 日期:只有年月日 2018/3/20
* 时间:只有时间 15:30:00
* 完整时间:年月日时 2018/3/20 15:30:00
*/
//1.建立一个Date对象
var date = new Date();
/*时间日期打印*/
//2.打印当前完整时间: (1)默认显示当前电脑的时区时间 (2)打印date时会自动转为字符串 date.toString()
console.log ( date );//Fri Mar 23 2018 20:45:15 GMT+0800 (中国标准时间)
//3.打印日期:标准版本
console.log ( date.toDateString () );//Fri Mar 23 2018
//4.打印日期:本地版本(当前电脑)
console.log ( date.toLocaleDateString () );// 2018/3/23
//5.打印当前时间:标准版本
console.log ( date.toTimeString () );//20:51:17 GMT+0800 (中国标准时间)
//6.打印当前时间:本地版本
console.log ( date.toLocaleTimeString () );//下午8:51:17
/*年月日时打印*/
//1.打印当前年份
console.log ( date.getFullYear () );//2018
//2.打印当前月份 范围:0-11 表明 1-12月
console.log ( date.getMonth () );//2 表明下标2 也就是3月
//3.打印当前日
console.log ( date.getDate () );//23
//4.打印当前星期 范围0-6 表明星期天-星期六
console.log ( date.getDay () );//5
//5.打印时
console.log ( date.getHours () );
//6.打印分
console.log ( date.getMinutes () );
//7.打印秒
console.log ( date.getSeconds () );
/**建立自定义日期*/
var date1 = new Date(2020,0,1,12,3,5);//依次传入 年,月,日,时,分,秒
console.log ( date1 );//Wed Jan 01 2020 12:03:05 GMT+0800 (中国标准时间)
var date2 = new Date("2022-05-06 12:03:35");
console.log ( date2 );//Fri May 06 2022 12:03:35 GMT+0800 (中国标准时间)
</script>
复制代码
数组经常使用api
<script>
//咱们建立了一个数组对象。此时它就已经拥有了内置对象全部的属性和方法
var arr = [10,20,30];
console.log ( arr.length );//访问数组对象的length属性
//1.链接多个数组:将另外一个数组的全部元素都添加到arr的后面
console.log ( arr.concat ( [ 40, 50 ] ) );//[10,20,30]
//2.将数组中的每个元素都拼接成一个字符串
var str = arr.join();//10,20,30
console.log ( str );
//3.删除数组的最后一个元素
arr.pop()//删除数组的最后一个元素
console.log ( arr );//[10,20]
//3.往数组的最后面添加一个元素
arr.push(100);
console.log ( arr );//[10,20,100]
//4.翻转数组
var newArr = arr.reverse();
console.log ( newArr );//[100,20,10]
//5.删除数组的第一个元素
arr.shift();
console.log ( arr );//[20,10]
//6.查找一个数组中的某些元素
var arr1 = [10,20,70,40,50,60];
// 第一个参数:start:从那一个下标开始查找 若是为负数则倒着查找
//第二个参数: end : 结束位置 start <= 范围 < end
console.log ( arr1.slice ( 1, 3 ) );//
//7.数组排序
//数组排序方法的参数是一个回调函数:告诉数组内置对象你的排序规则
//从小到大排序
var sortArr = arr1.sort(function (a,b)
{
return a - b
});
console.log ( sortArr );//从小到大
console.log ( sortArr.reverse () );//从大到小 (将从小到大排序好的数组翻转一下便可)
</script>
复制代码
字符串恒定性
<script>
//string恒定性:字符串是不能够被修改的
//验证:字符串是不能够被修改的
var str = '飞飞哥我爱你';
str[3] = '恨';
console.log ( str );
//结论:调用字符串任何的API的时候,都用新的字符串去接收
var str1 = str.replace('我爱你','么么哒');
//生成一个新的
console.log ( str1 );//字符串的任何API都是返回一个新的字符串,不能改变自身的
console.log ( str );//字符串不可修改
//容易混淆:遍历赋值操做与字符串恒定性搞混淆
var s1 = 'abc';
s1 += 'bbb';//这行代码的意思不是去修改abc,而是将abc+bbb拼接的新字符串赋值给s1
console.log ( s1 );//abcbbb
</script>
复制代码
字符串经常使用API介绍
<script>
//字符串经常使用API介绍
var str = "爱你么么哒!";
//1 获取字符串长度
var length = str.length;
console.log ( length );
//2 获取字符串某一个下标字符 (字符串至关于一个伪数组)
console.log ( str[ 4 ] );
console.log ( str.charAt(4) ); charAt(下标)函数至关于`字符串[下标]`
//3 拼接字符串
var str1 = str.concat("今晚一块儿吃鸡");//这行代码等价于 var str1 = str + "今晚一块儿吃鸡";
console.log ( str );
console.log ( str1 );
//4 判断一个字符串在不在某个字符串里面
var index1 = str.indexOf("爱");//若是存在,则返回参数字符串首字母所在的下标
var index2 = str.indexOf("你");
var index3 = str.indexOf("哟");//若是不存在,则返回 -1
console.log ( index1, index2, index3 );
//5 截取字符串 第一个参数:从哪一个下标开始截取 第二个参数:截取的长度
var str2 = str.substr(2,4);
console.log ( str2 );
//6 修改字符串 第一个参数:要修改的字符串 第二个参数:修改后的字符串
var str3 = str.replace("哒","啪");
console.log ( str );
console.log ( str3 );
//7 大小写转换 (只有英文才有大小写,中文不存在大小写)
console.log ( "AKlkshflsLKJHDHL".toLowerCase () );//转为小写 aklkshflslkjhdhl
console.log ( "AKlkshflsLKJHDHL".toUpperCase () );//转为大写 AKLKSHFLSLKJHDHL
console.log ( "中文不存在大小写".toLowerCase () );//转为小写
//8 分隔字符串:将字符串按照指定的符号分隔,获得一个数组
var str4 = "我&爱&你";
//这个函数的返回值必定是一个数组
var arry = str4.split("&");//以&符号分隔字符串 [我,爱,你]
console.log ( arry );// [我,爱,你]
console.log ( str4.split ( ":" ) );//["我&爱&你"] 若是字符串中没有这个分隔符 也会获得一个数组
</script>
复制代码
/**
* json对象与js对象外观上惟一的区别: json对象的属性和值都须要双引号,js对象不须要
* 为何要有json对象:由于在实际开发中,后台并非只是为了前端服务,他们还须要为java和ios服务
若是直接返回一个js对象,那么其余语言没法转换,为了统一,因此会返回给咱们一个json对象,这样前端/安卓/ios均可以识别
*
*/
//后台一般返回数据是一个json对象:为了让不一样语言的平台达到数据统一性
//1.json对象,不管键仍是值,不管什么数据类型须要双引号(不识别数据类型,都是字符串)
var json = {
"name" : "张三",
"age" : "18",
}
//2.js对象是javascript语言中的对象(识别数据类型)
var js = {
name : "张三",
age : 18,
}
//他们在打印的时候都是object对象类型,几乎没什么区别
console.log ( json );
console.log ( js );
复制代码
<script>
/*1.只有对象才有点语法,为何字符串也可使用点语法呢?
* 2.基本包装类型:为了方便操做基本数据类型,JavaScript还提供了三个特殊的引用类型:String/Number/Boolean
* `new String()`
* `new Number()`
* `new Boolean()`
* 三种基本包装类型中,Number与Boolean基本不用,最经常使用的就是string对象
* 3.基本包装类型的工做原理:了解便可
* (1)基本数据类型调用函数API时,会先把基本数据类型包装成临时的对象
* (2)而后这个对象调用函数
* (3)调用完函数以后再销毁对象
*/
// //基本包装类型: Number(),String(),Boolean()
var num = 10;
//上面这行代码,至关于编译器帮咱们作了一件事: var num = new Number(10)
num.toString() ;
var bol = true;//var bol = new Boolean(true)
bol.toString();
var str = 'abcd';//var str = new String('abcd')
str.toString();
</script>
复制代码
转义符:改变原来符号的做用就叫转义符
/**
* 转义符: `\` 改变原来符号的做用就叫转义符
* \" :输出双引号 * \t:水平制表符,说人话就是多打几个空格 * \n:换行符 * \\:显示一个\ * */ console.log ( "出来混了\\那么多年,从最开始的3万,到后来的五万,最后十五万,\n我也\"没有\"想到\t我最后会欠这么多钱");//出来混了\那么多年,从最开始的3万,到后来的五万,最后十五万,
//我也"没有"想到 我最后会欠这么多钱
复制代码
<script>
/**
* 1.逗号运算符: ,
* 2.逗号表达式:(表达式1,表达式2,表达式3.............)
* 一般与小括号一块儿使用,逗号用于链接算式,逗号
* 3.运算规则:
* (1)逗号运算符链接的每个式子都会执行
* (2)逗号运算式的结果是最终一个式子的结果
*/
var n1 = 10;
var n2 = 20;
var res = (n1++, n1 + n2);
// 10/11 , 11 + 20
console.log ( res );//31 逗号运算符的结果是最后一个算式的结果
console.log ( n1 );//11
console.log ( n2 );//20
</script>
复制代码