变量声明方式
- let
- let具有块级作用域有效,在块级作用域外无法访问,具体看下面例子
//let
if (true) {
//使用var定义变量a
var a = 0;
//使用let定义变量b
let b = 1;
//在块级作用域内打印b
console.log("作用域内:b=" + b); // 结果:作用域内:b=2
}
//在块级作用域打印a
console.log("a=" + a); //结果 a=2
//在块级作用外打印b
//console.log("b=" + b); //b is not defined
//let在for循环中的使用;定义一个数组接受一个函数,在函数中输出i的值
var fn = [];
for (var i = 0; i < 3; i++) {
fn[i] = function() {
console.log(i);
}
}
//调用函数
fn[0](); //结果输出3
fn[1](); //结果输出3
//同样情况下把var改为 let
for (let i = 0; i < 3; i++) {
fn[i] = function() {
console.log(i);
}
}
fn[0](); //结果输出0
fn[1](); //结果输出1
/暂时性死区
//在外部定义一个变量
var d = 7; {
//在块级作用域调用
console.log(d); //结果:报错,Cannot access 'd' before initializationat index.html: 46(anonymous) @ index.html: 46
//在调用后使用let重新声明
let d = 8;
}
//在块级作用域中调用变量d的时候,找不到d,这就叫:暂时性死区
/**
* 总结:
* 1、let声明的变量具有块级作用域
* 2、在循环中使用let定义的变量,在函数中调用时,会去相应的块级作用中查找
*/
- const
const用于声明一个常量,声明后的常量无法重新赋值;实际上,用const声明的常量是内存地址固定。具体看下面的例子
{
//使用const声明一个变量
const pi = 3.14;
//重新对变量赋值
pi = 3.15; //结果:报错,Assignment to constant variable
//使用const定义一个数组
const arr = [1, 2];
//输出该数组
console.log(arr); //结果:[1,2]
//对数组中的值进行修改
arr[1] = 3;
//重新输出
console.log(arr); //结果:[1,3],数组以被修改
//对数组重新赋值
arr = [1, 4]; //结果:报错,Assignment to constant variable
}
//在块级外输出const定义的变量
console.log(pi); //结果:pi is not defined
//总结:
//1、const定义的是一个常量,并且具有块级作用域有效的特点
//2、const定义的常量不能重新赋值
//3、const定义的数组类型,可以对数组的元素进行修改,但是不能对数组进行修改;这是由于用const定义的常量在内存中的位置固定
//如果学过c语言的话,const的性质和C语言中的宏差不多
var let const的区别
变量提升 | 全局变量 | 重新赋值 | 暂时死区 | 只声明不初始化 | |
---|---|---|---|---|---|
var | √ | √ | √ | × | √ |
let | × | × | √ | √ | √ |
const | × | × | × | √ | × |
解构赋值
- 先看例子
-
//定义一个数组 var arr = [1, 2, 3]; //之前赋值 var a = arr[0]; var b = arr[1]; //解构赋值 var [a, b, c] = arr; console.log(a); //结果:1 console.log(b); //结果:2 console.log(c); //结果:3 //使用解构赋值交换两个变量的值 let d = 1; let e = 2; console.log(d); //结果:1 console.log(e); //结果:2 [d, e] = [e, d]; console.log(d); //结果:2 console.log(e); //结果:1 //解构对对象也适用 let person = { name: "zhangsan", age: 23 }; let [name, age] = person; console.log(name); //结果:zhangsan console.log(age); //结果:23 //对象结构重命名 let { name: myname, age: myage } = person; console.log(myname); //结果:zhangsan console.log(myage); //结果:23 </script>
解构赋值能够将数组/对象中的元素分别进行赋值,也可以用于变量值的交换
箭头函数
//箭头函数
//原来的函数
var fn = function(ss) {
console.log(ss);
}
//箭头函数
var fn = (ss) => {
console.log(ss);
}
fn("成功!"); //结果:成功!
//如果函数只有一个参数,小括号可以省略;如果只有一条语句,大括号可以省略
//所以上面的函数可以简写为
fn = ss => console.log(ss);
fn("你好!"); //结果:你好!
//原来函数的this
var person = {
name: "zhangsan",
fn: function() {
console.log(this);
}
}
person.fn(); //结果,person对象
//箭头函数的this
var person = {
name: "zhangsan",
fn: () => {
console.log(this);
}
}
person.fn();//window对象
箭头函数是原来函数的简写,同时,箭头函数没有this指向,arguments,super或 new.target;箭头函数也不能用作构造函数
剩余参数
看例子
//剩余参数
//函数传递参数时,如果参数过多,可以使用数组来接收
var fn = function(a, b, ...args) {
console.log(a);
console.log(b);
console.log(args); //结果:输出 [3,4]
}
fn(1, 2, 3, 4);
//剩余参数与解构配合使用
let s = [1, 2, 3, 4, 5];
let [a, ...arr] = s;
console.log(a); //结果1
console.log(arr); //结果 [2,3,4,5]
剩余参数用数组收多余的参数,也可以配合解构生成原数组的子数组
扩展操作符
扩展操作符可以将数组序列化为以逗号间隔的序列
//扩展操作符
var arr = [1, 2, 3, 4, 5, 6];
//扩展操作符可以将数组序列化为以逗号间隔的序列
console.log(...arr); //输出:1 2 3 4 5 6
// 扩展运算符的应用
var arr1 = [2, 4, 6, 8, 9];
//利用扩展运算符合并数组
arr = [...arr, ...arr1];
console.log(arr); //结果为合并后的数组
Array 对象的扩展
- Array.form()
- Array.form() 将伪数组转换为数组
//Array的扩展函数
//Array.form() 将伪数组转换为数组
var arrayLike = {
0: 1,
1: 1,
2: "2",
length: 3,
}
var arr = Array.from(arrayLike);
console.log(arr); //结果:[1,1,"2"]
//可以传递第二个参数,参数时一个函数,函数用来对伪数组中的数值进行操作
var arr = Array.from(arrayLike, (item) => {
return item * 2;
});
console.log(arr); //结果:[2,2,4]
- Array.of()
- Array.of() 方法创建一个具有可变数量参数的新数组实例,而不考虑参数的数量或类型。返回值一个新的数组
//Array.of() 方法创建一个具有可变数量参数的新数组实例,而不考虑参数的数量或类型。返回值一个新的数组
var arr = Array.of(1);
console.log(arr); //结果: [1]
arr = Array.of(1, 2, 3);
console.log(arr); //结果:[1, 2, 3]
//Array()与Array.of()的区别
arr = Array(7);
console.log(arr); //结果:[empty × 7] 有7个元素的空数组
arr = Array.of(7);
console.log(arr); //结果:[7],有一个元素为的数组
- Array.copyWithin()
- copyWithin() 方法浅复制数组的一部分到同一数组中的另一个位置,并返回它,不会改变原数组的长度。
//Array.prototype.copyWithin()
//copyWithin() 方法浅复制数组的一部分到同一数组中的另一个位置,并返回它,不会改变原数组的长度。
/*copyWithin()有三个参数:
*1.要复制到的位置,如果该参数为负值,位置将从最后开始计算
*2.复制开始位置
*3.复制结束位置*/
arr = [1, 2, 3, 4, 5, 6, 7, 8];
console.log(arr.copyWithin(-1, 3, 5)); //结果:[1, 2, 3, 4, 5, 6, 7, 4]
- Array.find()
- find() 方法返回数组中满足提供的测试函数的第一个元素的值。 否则返回 undefined。
- 参数为一个函数,这个函数会在数组每一项上执行,这个函数可以接受四个参数
- 1.element:当前遍历到的元素
- 2.index:当前遍历到元素的索引(可选)
- 3.array:数组本身(可选)
- 4.thisArg:执行时作用的this对象(可选)
- 返回值:数组中第一个满足所提供测试函数的元素的值,否则返回 undefined。
//Array.prototype.find()
//find() 方法返回数组中满足提供的测试函数的第一个元素的值。 否则返回 undefined。
//参数为一个函数,这个函数会在数组每一项上执行,这个函数可以接受四个参数
/*
*1.element:当前遍历到的元素
*2.index:当前遍历到元素的索引(可选)
*3.array:数组本身(可选)
*4.thisArg:执行时作用的this对象(可选)
*/
//返回值:数组中第一个满足所提供测试函数的元素的值,否则返回 undefined。
var arr = [1, 2, 3, 4, 5, 6, 7, 8];
arr.find(element => console.log(element)); //遍历整个数组
arr.find((element, index) => console.log(element * index)); //遍历整个数组,并让每个元素与自己的索引相乘
//寻找数组中的质数
function isPrime(element, index, array) {
if (element > 1) {
for (let i = 2; i <= Math.sqrt(element); i++) {
if (element % i < 1) {
return false;
}
}
}
return element > 1;
}
console.log(arr.find(isPrime)); //结果:2
- Array.findIndex()
- 返回第一个满足条件的索引
- 参数:处理数组元素的函数,函数执行时会自动传出下面的参数:
- 1.element
- 当前元素。
- 2.index
- 当前元素的索引。
- 3.array
- 调用findIndex的数组。
- 4.this
- 可选。执行callback时作为this对象的值.
- 1.element
-
返回值:数组中通过提供测试函数的第一个元素的索引。否则,返回-1
/**
Array.prototype.findIndex()
返回第一个满足条件的索引
参数:处理数组元素的函数,函数执行时会自动传出下面的参数:
1.element
当前元素。
2.index
当前元素的索引。
3.array
调用findIndex的数组。
4.this
可选。执行callback时作为this对象的值.
返回值:数组中通过提供测试函数的第一个元素的索引。否则,返回-1
*/
var arr = [1, 2, 3, 4, 5];
function isPrime(element, index, array) {
if (element > 1) {
for (let i = 2; i <= Math.sqrt(element); i++) {
if (element % i < 1) {
return false;
}
}
}
return element > 1;
}
console.log(arr.findIndex(isPrime));
- Array.fill()
- fill() 方法用一个固定值填充一个数组中从起始索引到终止索引内的全部元素。不包括终止索引。
- 参数:
- 1.value
- 填充数组的值
- 2.start(可选)
- 开始索引
- 3.end(可选)
- 结束索引(不包括)
- 如果不传递后两个参数,默认为全部
- 如果只传递开始索引,默认从开始索引开始,到数组结束
- 返回值:
- 改变后的数组
- 1.value
//Array.prototype.fill()
/*
fill() 方法用一个固定值填充一个数组中从起始索引到终止索引内的全部元素。不包括终止索引。
参数:
1.value
填充数组的值
2.start(可选)
开始索引
3.end(可选)
结束索引(不包括)
如果不传递后两个参数,默认为全部
如果只传递开始索引,默认从开始索引开始,到数组结束
返回值:
改变后的数组
*/
var arr = [1, 2, 3, 4];
console.log(arr.fill(0)); //只传递值;结果:[0,0,0,0]
console.log(arr.fill(0, 2)); //传递值和开始索引;结果:[1,2,0,0]
console.log(arr.fill(0, 1, 3)); //传递全部参数;结果:[1, 0, 0, 4]
- 下面三个比较像,所以放到一起
- Array.keys()
- keys() 方法返回一个包含数组中每个索引键的Array Iterator对象。
- Array.values()
- values() 方法返回一个新的 Array Iterator 对象,该对象包含数组每个索引的值
- Array.entries()
- entries() 方法返回一个新的Array Iterator对象,该对象包含数组中每个索引的键/值对。
- 具体看代码吧
- Array.keys()
/*
Array.prototype.keys()
keys() 方法返回一个包含数组中每个索引键的Array Iterator对象。
参数:无
返回值:一个新的 Array 迭代器对象。
*/
var arr = [1, 2, 3, 4];
console.log(...arr.keys()); //结果:0,1,2,3
/**
Array.prototype.values()
values() 方法返回一个新的 Array Iterator 对象,该对象包含数组每个索引的值
参数:无
返回值:一个新的 Array 迭代器对象。
与keys差不多,一个时返回索引的迭代器对象,一个是返回值的迭代器对象
*/
var arr = [1, 2, 3, 4];
console.log(...arr.values()); //结果:1,2,3,4
/*
Array.prototype.entries()
entries() 方法返回一个新的Array Iterator对象,该对象包含数组中每个索引的键/值对。
参数:无
返回值:一个新的 Array 迭代器对象。
*/
var arr = [1, 2, 3, 4];
console.log(...arr.entries()); //结果:一个二维数组,包含数组的索引和对应的值
模板字符串
-
在es6之前拼接字符串需要使用 + 号
-
在es6中可以使用模板字符串
-
模板字符串的定义:
-
使用esc键下的点 并使用 $ 符号替换接入的字符串
// 模板字符串
var name = "张三";
var age = 23;
var s = `我的名字是${name},我的年龄为${age}`;
console.log(s); //结果:我的名字是张三,我的年龄为23
模块化(Module)
- 在es6之前JavaScript没有模块化的概念,但是在es6中加入了模块化的概念
模块化就是将一个函数或一段代码段独立出来,在需要使用的时候导入,具体,看例子
// model.js
var fn = function(info) {
console.log(info);
}
//使用exports向外暴露一个对象
exports.default = fn;
// main.js
//使用es6的import导入模块
import fn form './model.js'
fn("你好");
- 目前,各大浏览器都还不支持import导入模块,因此,需要各种前端打包工具进行代码转换
for...of
-
for...of语句在可迭代对象(包括 Array,Map,Set,String,TypedArray,arguments 对象
-
var arr = [1, 2, 3, 4, 5]; for (var e of arr) { console.log(e); //结果:1,2,3,4,5 }