+与,的区别
let name = "赵志伟";
console.log("name=", name);//使用逗号可以输出对象的完整信息
console.log("name=" + name);//使用加号, 类似于字符串的拼接. 如果name是对象, 输出的就是object, 而不会输出对象的完整信息
细节1. let声明的变量有严格的局部作用域
//var声明的变量, 在代码块中, 作用域没有限制
//let声明的变量, 在代码块中, 则作用域在代码块中
{
var name = "赵志伟";
let job = "java工程师";
console.log("name= ", name);
console.log("job= ", job);
}
console.log("name= ", name);
console.log("job= ", job);//job is not defined
细节2. var 可以声明多次; let 只能声明一次
var num1 = 100;
var num1 = 200;
console.log("num1= ", num1);
let num2 = 300;
//SyntaxError 语法错误
let num2 = 400;//SyntaxError: redeclaration of var num1
console.log("num2= ", num2);
细节3. var 存在变量提升; let 不存在变量提升
console.log("x= ", x);//ReferenceError: x is not defined
console.log("y= ", y);//y= undefined[认你这个变量, 不过变量现在还没有值]
var y = "mary";
console.log("z= ", z);//ReferenceError: can't access lexical declaration 'z' before initialization
let z = "mary";
常量在定义时, 需要赋值; 常量赋值后不能修改
const PI;//SyntaxError: missing = in const declaration
const PI = 3.14;
PI = 3.1415;//TypeError: invalid assignment to const 'PI'
console.log("PI=", PI);
传统方式解构
let arr = ["赵志伟",23,"java工程师"];
//如果要看某个变量的类型[,会把所有信息都打印出来]
console.log("arr=>", arr);
//数组解构
// ※传统方式
let x = arr[0], y = arr[1], z = arr[2];
console.log(x, y, z);
console.log("=============================================");
ES6风格解构
// ※ES6风格
let [a, b, c] = arr;
console.log(a, b, c);
console.log("=============================================");
let [num1, num2, num3] = ["赵志伟",23,"java工程师"];
console.log(num1, num2, num3);
传统方式解构
//monster是一个对象
let monster = {name: "美猴王", age: 30000};
//传统方式解构[取出属性]
console.log(monster.name, " ", monster.age);
ES6对象解构
//ES6对象解构
//1.把monster对象的属性, 依次赋值给{name,age}
//2.{name,age}的取名name, age要和monster对象的属性名保持一致
//3.要使用{ }, 不要使用[]
//4.{name,age} 里面的顺序是无所谓的
let monster = {name: "美猴王", age: 30000};
let {name, age} = monster;
console.log("name=", name, " age=", age);
console.log("===================================");
//下面这个写法也可以
// let {name, age} = {name: "牛魔王", age: 35000};
//还有其它的形式, 比如方法上使用对象解构
//如果这样使用, 仍然要保证 {}名称 和对象的属性名一致
function f1({name, age}) {
console.log("f1-name=", name, " ", "f1-age=", age);
}
f1(monster);
字符串, 换行会原生输出
//1.字符串, 换行会原生输出
let str1 = `for(int i = 0; i < 10; i++) {
System.out.println("i=" + i);
}`;
console.log("str1=", str1);
字符串插入变量和表达式. 变量名写在 ${} 中, ${} 中可以放入 JavaScript 表达式
//2.字符串插入变量和表达式. 变量名写在 ${} 中, ${} 中可以放入 JavaScript 表达式
let name = "赵志伟";
//(1)当解析 ${name} 时, 就找最近的name变量, 进行替换
//(2)然后可以得到最后解析的字符串
let str2 = `我是${name}`;
let str3 = `1+2=${1 + 2}`;
let n1 = 80;
let n2 = 20;
let str4 = `${n1}+${n2}=${n1 + n2}`;
console.log("str2=", str2);
console.log("str3=", str3);
console.log("str4=", str4);
字符串中调用函数
//3.字符串中调用函数
function hello(name) {
return "hello, " + name;
}
let name2 = "mary";
let str5 = `hello() 返回的结果是=${hello("赵志伟")}`;
let str6 = `hello() 返回的结果是=${hello(name2)}`;
console.log("str5=", str5);
console.log("str6=", str6);
const age = 23;
const name = "赵志伟";
//传统 声明.定义对象
let monster = {name: name, age: age};
//ES6 声明.定义对象
//1.{name,age}: 表示对象的属性名是name和age
//2.属性name,age的值是从常量/变量 name,age来的
let monster2 = {name, age};
console.log("monster2=", monster2);
传统-对象方法定义
//传统-对象方法定义
let monster = {
name: "玉皇大帝",
age: 10000000,
sayHi: function () {
console.log("信息: name=", this.name, " age=", this.age);
}
}
monster.f2 = function () {
console.log("f2()");
}
monster.sayHi();
monster.f2();
ES6-对象方法定义
let monster2 = {
name: "红孩儿~",
age: 2000000,
sayHi() {
console.log("信息: name=", this.name, " age=", this.age);
},
f1() {
console.log("f1() ");
}
}
monster2.sayHi();
monster2.f1();
拷贝对象-深拷贝
// let cat2 = cat;对象的引用
// cat2.name = "大花猫";
// console.log("cat=", cat);
// console.log("cat2=", cat2);
//拷贝对象-深拷贝
let cat2 = {...cat};
cat2.name = "中华田园猫";
console.log("cat=", cat);
console.log("cat2=", cat2);
合并对象-深拷贝
//合并对象-深拷贝
let monster = {name: "白骨精", age: 100};
let car = {brand: "奔驰", price: 10000};
let monster_car = {...monster, ...car};
monster_car.name = "狐狸精";
console.log("monster=", monster);
console.log("monster_car=", monster_car);
传统
//传统
var f1 = function (n) {
return n * 2;
}
console.log("传统方式=", f1(3));
ES6, 箭头函数使用
//ES6, 箭头函数使用
let f2 = (n) => {
return n * 2;
}
console.log(f2);
console.log("箭头函数=", f2(999));//1998
//上面的ES6函数写法, 还可以简写
let f3 = (n) => n * 2;
let f4 = n => n * 2;
console.log("f3=", f3(100));
console.log("f4=", f4(400));
//函数也可以传给一个变量
function hi(f5) {
console.log(f5(900));
}
hi(n => n + 1);
hi((n) => {
return n - 1;
})
案例二: 传统函数改造成箭头函数
//传统
let f1 = function (n, m) {
let res = 0;
for (let i = n; i <= m; i++) {
res += i;
}
return res;
};
//ES6, 箭头函数使用
let f2 = (n, m) => {
let res = 0;
for (let i = n; i <= m; i++) {
res += i;
}
return res;
};
console.log("f2=", f2(1, 10));
案例三: 箭头函数+对象解构
const monster = {
name: "美猴王",
age: "30000",
skill: ["筋斗云", "火眼金睛"]
};
//要求: 在方法形参取出monster对象的skill属性
//传统方式
let f1 = function (monster) {
console.log("skill=", monster.skill);
}
f1(monster);
//箭头函数
let f2 = ({skill}) => {
console.log("skill=", skill);
}
//1.f2传入对象 monster
//2.f2形参是 {skill}, 所以根据ES6的对象解构特性, 会把monster对象skill属性赋给 skill
//3.对象解构的前提 {skill}的skill和 monster 的skill属性名一致
f2(monster);
//箭头函数+解构: 注意有{}, skill名称需要和对象属性名一致
//{} 去掉后, monster会赋给name, 所以{}必须带上才能结构
let f3 = ({name, age, skill}) => {
console.log("name=", name, " ", "age=", age, " ", "skill=", skill);
}
f3(monster);
let cat = {name: "喵喵~", age: 3};
let str = `这是一只小花猫, 名字叫${cat.name}, 年龄${cat.age}岁`;
console.log("str=", str);
let dog = {name: "旺财", age: 5};
let {namex, age} = dog;
console.log("namex=", namex, " age=", age);
let name = "周星驰";
let job = "喜剧演员";
let star = {
name,
job,
show() {
console.log("star信息为 name=", this.name, " job=", this.job);
}
};
star.show();
var cal = {
oper: "*",
arr: [1, 2, 3, 4, 5]
};
let f1 = ({oper, arr}) => {
if (arr == null || arr.length <= 0) {
console.log("数据为空");
return;
}
if (arr.length == 1) {
console.log("result=", arr[0]);
return;
}
let result = arr[0];
switch (oper) {
case "+":
for (let i = 1; i < arr.length; i++) {
result += arr[i];
}
console.log("result=", result);
break
case "-":
for (let i = 1; i < arr.length; i++) {
result -= arr[i];
}
console.log("result=", result);
break
case "*":
for (let i = 1; i < arr.length; i++) {
result *= arr[i];
}
console.log("result=", result);
break
case "/":
for (let i = 1; i < arr.length; i++) {
result /= arr[i];
}
console.log("result=", result);
break
}
};
f1(cal);
let f8 = (arr, fun) => {
console.log("结果=", fun(arr));
}
f8([1, 2, 3], (arr) => {
let sum = arr[0];
for (let i = 1; i < arr.length; i++) {
sum += arr[i];
}
return sum;
});
data/monster.json
{
"id": 1,
"name": "唐僧"
}
data/monster_detail_1.json
{
"id": 1,
"address": "东土大唐",
"skill": "阿弥陀佛",
"age": 30000,
"gf_id": 2
}
monster_girlfriend_2.json
{
"id": 2,
"name": "女儿国国王",
"age": 30000
}
ajax.html
//jquery发出ajax请求
$.ajax({
url: "data/monster.json",
//下面是ES6对象方法简写形式
success(resultData) {//成功回调处理函数
console.log("第1次ajax请求 monster基本信息=", resultData);
//发出第二次ajax请求
$.ajax({
url: `data/monster_detail_${resultData.id}.json`,//模板字符串
success(resultData) {
console.log("第2次ajax请求 monster详细信息=", resultData);
//$.ajax => Callback Hell
//$.ajax
//$.ajax
},
error(err) {
console.log("第2次ajax请求出现异常 异常信息=", err);
}
})
},
error(err) {
console.log("第1次ajax请求出现异常 异常信息=", err);
},
})
//先请求到monster.json
let p = new Promise((resolve, reject) => {
//发出ajax请求
$.ajax({
url: "data/monster.json",
success(resultData) {//成功回调函数
console.log("promise发出的第1次ajax请求 monster基本信息=", resultData);
resolve(resultData);
},
error(err) {
console.log("promise发出的异步请求异常=", err);
},
});
})
//在这里我们可以继续编写请求成功后的业务
p.then((resultData) => {
//这里我们可以继续发出请求
// console.log("p.then 得到 resultData", resultData);
$.ajax({
url: `data/monster_detail_${resultData.id}.json`,//模板字符串
success(resultData) {//第二次ajax请求成功的回调函数
console.log("第2次ajax请求 monster的详细信息=", resultData);
},
error(err) {//第2次ajax请求失败的回调函数
console.log("第2次promise发出异步请求异常, 异常信息=", err);
}
})
});
let p = new Promise((resolve, reject) => {
//发出ajax请求
$.ajax({
url: "data/monster.json",
success(resultData) {//成功回调函数
console.log("promise发出的第1次ajax请求 monster基本信息=", resultData);
resolve(resultData);
},
error(err) {
// console.log("第1次promise发出异步请求异常, 异常信息=", err);
reject(err);
},
});
});
//在这里我们可以继续编写请求成功后的业务
p.then((resultData) => {
//这里我们可以继续发出请求
// console.log("p.then 得到 resultData", resultData);
return new Promise((resolve, reject) => {//第二次错误被捕获, 但是没有输出信息, 原因:这里没加return
$.ajax({
url: `data/monster_detail1_${resultData.id}.json`,//模板字符串
success(resultData) {//第二次ajax请求成功的回调函数
console.log("第2次ajax请求 monster的详细信息=", resultData);
//继续进行下一次的请求
},
error(err) {//第2次ajax请求失败的回调函数
// console.log("第2次promise发出异步请求异常, 异常信息=", err);
reject(err);
}
})
})
}).catch((err) =>{//这里可以对多次ajax请求的异常进行处理
console.log("promise异步请求异常=", err);
});
//在这里我们可以继续编写请求成功后的业务
p.then((resultData) => {
//这里我们可以继续发出请求
// console.log("p.then 得到 resultData", resultData);
return new Promise((resolve, reject) => {//第二次错误被捕获, 但是没有输出信息, 原因:这里没加return
$.ajax({
url: `data/monster_detail_${resultData.id}.json`,//模板字符串
success(resultData) {//第二次ajax请求成功的回调函数
console.log("第2次ajax请求 monster的详细信息=", resultData);
//继续进行下一次的请求
resolve(resultData);
},
error(err) {//第2次ajax请求失败的回调函数
// console.log("第2次promise发出异步请求异常, 异常信息=", err);
reject(err);
}
})
})
}).then((resultData) => {
// console.log("p.then().then, resultData=", resultData);
//即 可以在这里发出第3次 ajax请求 => 获取该妖怪的女友信息
return new Promise((resolve, reject) => {
$.ajax({
url: `data/monster_girlfriend_${resultData.gf_id}.json`,//模板字符串
success(resultData) {//第二次ajax请求成功的回调函数
console.log("第3次ajax请求 monster的女友信息=", resultData);
//继续进行下一次的请求
resolve(resultData);
},
error(err) {//第2次ajax请求失败的回调函数
// console.log("第2次promise发出异步请求异常, 异常信息=", err);
reject(err);
}
})
})
}).catch((err) => {//这里可以对多次ajax请求的异常进行处理
console.log("promise异步请求异常=", err);
});
/**
* 这里将重复的代码, 抽出来, 编写一个方法get
* @param url ajax请求的资源
* @param data ajax请求携带的数据
* @returns {Promise}
*/
function get(url, data) {
return new Promise((resolve, reject) => {
$.ajax({
url: url,
data: data,
success(resultData) {
resolve(resultData);
},
error(err) {
reject(err);
},
})
})
}
//需求:完成
//1.先获取monster.json
//2.获取monster_detail_1.json
//3.获取monster_girlfriend_2.json
get("data/monster.json").then((resultData) => {
//第1次ajax请求成功后处理代码
console.log("第1次ajax请求返回数据=", resultData);
return get(`data/monster_detail_${resultData.id}.json`);
}).then((resultData) => {
//第2次ajax请求成功后处理代码
console.log("第2次ajax请求返回数据=", resultData);
return get(`data/monster_girlfriend_${resultData.gf_id}.json`);
}).then((resultData) => {
//第3次ajax请求成功后处理代码
console.log("第3次ajax请求返回数据=", resultData);
}).catch(err => {//箭头函数只有一个参数, 可以不用()小括号
console.log("promise请求异常=", err);
})
分别使用jquery-ajax 和 promise代码重排, 完成如下功能. 发出3次ajax请求, 获取对应的数据, 注意体会promise发出多次ajax请求的便利之处
ES5模块化编程也叫CommonJS模块化编程
module.exports={ } / exports={ }
导出模块, 使用 let/const 名称 = require("xx.js")
导入模块`需求说明
- 编写 functions.js, 该文件有函数, 变量, 常量, 对象, 数组…
- 要求在use.js中, 可以使用到function.js中定义的 函数/变量/常量/对象/数组
- 要求使用模块化编程的方式完成
function.js
//定义对象, 变量, 常量, 函数
const sum = function (num1, num2) {
return parseInt(num1) + parseInt(num2);
};
const sub = function (num1, num2) {
return parseInt(num1) - parseInt(num2);
};
let name = "赵志伟";
const PI = 3.14;
const monster = {
name: "铁扇公主",
age: 300,
sayHi() {
console.log("铁扇公主");
},
};
//导出
//1.module.exports 导出模块
//2.把要导出的数据, 写入到 { } 中即可
//3.可以全部导出, 也可以部分导出
//4.相当于把导出的数据当作一个对象
module.exports = {
sum: sum,
sub: sub,
myName: name
}
use.js
//导入
//1.在es5中, 我们通过 require 就把对应.js中的数据/对象, 引入
//2.我们使用的时候, 通过m.属性, 就可以使用
const m = require("./function");
//使用
//只要这里idea可以识别变量,函数,对象 说明没有问题
console.log(m.sub("1", "2"));
console.log(m.sum(33, 22));
console.log(m.myName);
简写
function.js
/*导出
1.module.exports 导出模块
2.把要导出的数据, 写入到 { } 中即可
3.可以全部导出, 也可以部分导出
4.相当于把导出的数据当作一个对象
5.如果属性名/函数/变量/对象..名字相同, 可以简写
6.有些前端, 简写 module.exports={} 成 exports={}
*/
exports = {
sum,
sub,
name,
PI
}
// module.exports = {
// sum,
// sub,
// name,
// PI
// }
// module.exports = {
// sum: sum,
// sub: sub,
// myName: name
// }
use.js
//导入
//1.在es5中, 我们通过 require 就把对应.js中的数据/对象, 引入
//2.我们使用的时候, 通过m.属性, 就可以使用
//3.如果我们导入时, 不需要所有的, 我们可以导入部分数据
const m = require("./function");//默认后缀js
const {sub} = require("./function");
//使用
//只要这里idea可以识别变量,函数,对象 说明没有问题
console.log(m.sub("1", "2"));
console.log(m.sum(33, 22));
console.log(m.name);
console.log(sub(10, 12));
export {名称 / 对象 / 函数 / 变量 / 常量}
(2)export 定义 =
(3)export default { }
导出模块import { } from "xx.js"
或者 import 名称 from "xx.js"
导入模块需求说明
- 编写common.js, 该文件有函数, 变量, 常量, 对象
- 要求在use_common.js, 可以使用到 common.js中定义的 函数/变量/常量/对象
- 使用ES6模块化编程的方式完成
common.js
//定义对象, 变量, 常量, 函数
const sum = function (num1, num2) {
return parseInt(num1) + parseInt(num2);
};
const sub = function (num1, num2) {
return parseInt(num1) - parseInt(num2);
};
let name = "赵志伟";
//ES6的导出模块/数据
/**
* 1.export 就是导出
* 2.可以全部导出, 也可以部分导出
*/
export {
sum,
sub,
name
}
use_common.js
/**导入
* 1.我们可以用 {} 来接收导出的数据
* 2.可以全部接收, 也可以选择接收
* 3.要求导入的名称 和 导出的名称一致
*/
import {sub, sum, name} from "./common";
//使用
console.log(sum(1, 3));
console.log(name);
common2.js
//定义对象, 变量, 常量, 函数
//定义sum函数时, 直接导出
//说明: 如果在定义时,导出的数据, 在导入时,要保持名称一致
export const sum = function (num1, num2) {
return parseInt(num1) + parseInt(num2);
};
use_common2.js
//可以导入模块/数据
import {sum} from "./common2";
//没有导出的数据, 是不可以导入的
import {sum2} from "./common2";
console.log(sum(10, 12));
common3.js
//定义对象, 变量, 常量, 函数
//演示默认导出
//如果是默认导出, 那么在导入的时候,使用的语法
//可以这么理解: 类似于把 {} 当作一个对象导出
export default {
sum(num1, num2) {
return parseInt(num1) + parseInt(num2);
},
sub(num1, num2) {
return parseInt(num1) - parseInt(num2);
},
}
use_common3.js
//导入默认导出的模块/数据
//好处是 m 名称是可以自己指定的
//因为m名字, 程序员可以自己指定, 因此我们就可以解决命名冲突的问题
import m from "./common3";
//使用 m.xx
console.log(m.sub(100, 200));
使用批量导出
zzwcommon.js
let cat = {
name: "喵喵~",
age: 2,
cry() {
console.log("花喵哭泣");
},
};
let dog = {
name: "旺财",
age: 3,
hi() {
console.log("汪汪");
},
};
// 批量导出
export {cat, dog};
use_zzwcommon.js
import {dog, cat} from "./zzwcommon";
console.log(cat.age);
console.log(cat.name);
cat.cry();
创建时, 直接导出
//定义时导出
export const cat = {
name: "喵喵~",
age: 2,
cry() {
console.log("花喵哭泣");
}
}
export const dog = {
name: "旺财",
age: 3,
hi() {
console.log("汪汪");
}
}
默认方式导出
zzwcommon.js
//默认方式导出
//这里注意 写法有一些变化, 把我们的两个对象当做 {} 的属性即可
export default {
cat: {
name: "喵喵~",
age: 2,
cry() {
console.log("花喵哭泣");
},
},
dog: {
name: "旺财",
age: 3,
hi() {
console.log("汪汪");
},
},
}
use_zzwcommon.js
//导入zzwcommon.js 默认导出的模块
import m from "./zzwcommon";
console.log(m.dog.age);
console.log(m.dog.name);
m.dog.hi();
b.js
//b.js中定义了dog对象
//方式一
export default {
dog: {
say() {
},
},
};
//方式二
let dog = {
say() {
},
};
export default {
dog: dog,
};
a.js
import m from "./b";
//a.js中的dog
const dog = {
hi() {
},
};
console.log(dog.hi());//a.js
console.log(m.dog.say());//b.js