Skip to content

语法

var关键字和变量提升

javascript 的变量是松散类型的,意思是可用于保存任何数据类型,每个变量只不过是一个用于保存任意值的命名占位符。

var关键字声明的是函数作用域

var声明提升:

 function fn() {
            console.log(name);
            var name = 12;
        }
        fn();//undefined

相当于:

function fn() {
			var name;
            console.log(name);
            name = 12;
        }
        fn();//undefined

因此不会报错,而是输出undefined

let声明

let声明的是块级作用域,块级作用域是函数作用域的子集,因此适用于var的作用域限制同样也适用于let.

let不允许同一个块级作用域中出现冗余声明,对声明冗余不会因为let和var混用而受影响。

if (true) {
            let age;
            let age;

            console.log(age);
        }
        console.log(age);

报错:Uncaught SyntaxError: Identifier 'age' has already been declared(age已经声明过了)

let出现的暂时性死区

let声明不会变量提升,在let变量声明之前不能以任何方式来引用为声明的变量。在let声明之前的执行瞬间被称为“暂时性死区”,都会抛出ReferenceError。

let在全局作用域中声明的变量不会成为windows的属性,而var声明则会成为window的属性。

for循环声明

var 声明的变量会渗透到for循环外部

 for (var index = 0; index < 5; index++) {
        }
  console.log(index);//5

let声明的变量不会渗透到for循环外部

 for (let index = 0; index < 5; index++) {
 
 }
  console.log(index);//index is not defined

在适用var声明变量时,对迭代变量的奇特声明和修改:

 for (var index = 0; index < 5; index++) {
            setTimeout(function() {
                console.log(index);//输出5个5
            }, 1);
        }

原因:是因为在退出循环时保存的是导致循环退出的值。改用let就不会有问题了。

const声明

1.const声明也是块级作用域

2.声明是必须赋值,后面不能再修改,相当于创建常量。

3.同let一样,不能重复声明。

数据类型

6种简单数据类型:

  1. 1.Undefined

  2. 2.Null

  3. 3,Bollean

  4. 4.Number

  5. 5.String

  6. 6.Symbol(es6新增,字符)

一种复杂数据类型:

  1. Object(对象)

null

undefined是由null派生过来的,因此他们表面上相等。由于他们的类型不同,所以不全等于。

js
console.log(null == undefined);//true
console.log(null === undefined);//false

Boolean

Boolean(变量)转型函数;

数据类型truefalse
Booleantruefalse
String非空字符串“”(空字符串)
Number非零数值(包括无穷值)0,NaN
Object任意对象null
Undefinedundefined

Number

浮点型只会保存近似值,因为对于有些小数,二进制是无法精确表示的。

Number.MIN_VALUE,最小值

Number.MAX_VALUE 最大值

infinity 无穷大

isFinite(变量)函数,判断是否在能表示范围内

isNaN(变量) 判断是否为NAN,如果是返回false,否则返回true,可以转换为数值的也为false

js
console.log(isNaN(NaN)); //true
console.log(isNaN(false)); //false
console.log(isNaN('19')); //false
console.log(isNaN("blrfea")); //true
console.log(isNaN(12));//false

number(变量 ): 转型函数,可用于任何数据类型,

转换规则:

  • 布尔值,true转为1,false转为0

  • 数值,直接返回

  • null,返回0

  • undefined 返回NaN

  • 字符串:空字符串返回0,纯数字字符放回相应的数值,其他的都返回NaN

parseInt(变量,进制数)

将开头有整数的部分转为转为整数。

parseFloat(变量):将开头有小数的部分转为小数。

只能解析十进制

String

字符串的特点:

ECMAscript中的字符串是不可变得,一旦创建,值就不能改变了。要想修改,必须先销毁原始的字符串。然后将新的字符串保存到该变量。

tostring(); 转换为字符串函数。(null,undefined没有tostring()方法。)

变量加上一个空字符也可以转换为字符串:

js
 let a = 321321;
  a = a + '';

模板字面量:保留换行符,可以换行定义字符串。

js
 let b = `feaf 
      feaf`;

模板字面量使用变量,插入值函数:${}

js
let c = `${a}+${b}=${a+b}`

Symbol类型

符号是原始值,且符号实例是唯一的,不可变的。符号的用途是确保对象属性使用唯一标识符,不会发生属性冲突的危险。

js
//a和b是不相等的
let a = Symbol();
let b = Symbol();
let c = Symbol('ab');//可以传入字符串参数,作为对符号的描述

全局注册表

创建时会在全局中检索是否存在对应的符号,如果存在就使用现有的,没有就创建新的。

所有的参数必须使用字符串,因此传给Symbol.for()的所有参数都会转换为字符串。

js
 let a = Symbol.for('symbol类型');
 let b = Symbol.for();
 console.log(b) //Symbol(undefined)

Symbol.keyFor();查询==全局==注册表,返回对应的字符串键。

js
let a = Symbol.for('abc');
console.log(Symbol.keyFor(a));//abc

使用符号作为属性的常用方法

Object.defineProperties() 方法直接在一个对象上定义新的属性或修改现有属性,并返回该对象。

js
let obj = {};
let b = Symbol("b");
let c = Symbol("c");

Object.defineProperties(obj, {
  [b]: {
    value: "cde val",
  },
  [c]: {
    value: "fff val",
  },
});

**Object.defineProperty()** 方法会直接在一个对象上定义一个新属性,或者修改一个对象的现有属性,并返回此对象。方法会直接在一个对象上定义一个新属性,或者修改一个对象的现有属性,并返回此对象。

js
let a = Symbol('abc');
let b = Symbol('cde');
let c = Symbol('fff');
let o = {
    one: 'hello',
    two: 'wird',
    [a]: 'abc val'
};

Object.defineProperty(o, b, {
    value: 'aaa'
});

**Object.getOwnPropertyNames()**方法返回一个由指定对象的所有自身属性的属性名(包括不可枚举属性但不包括Symbol值作为名称的属性)组成的数组。

js
let a = Symbol('abc');
let b = Symbol('cde');
let c = Symbol('fff');
let o = {
    one: 'hello',
    two: 'wird',
    [a]: 'abc val'
}; 

console.log(Object.getOwnPropertyNames(o));
 
 //(2) ["one", "two"]

**Object.getOwnPropertySymbols()** 方法返回一个给定对象自身的所有 Symbol 属性的数组。

js
let obj = {
  name: "wanmg",
  age: 12,
};
let b = Symbol("b");
let c = Symbol("c");

Object.defineProperties(obj, {
  [b]: {
    value: "cde val",
  },
  [c]: {
    value: "fff val",
  },
});

console.log(Object.getOwnPropertySymbols(obj));//[ Symbol(b), Symbol(c) ]

Object.getOwnPropertyDescriptors() 方法用来获取一个对象的所有自身属性的描述符。

js
let obj = {
  name: "wanmg",
  age: 12,
};
let b = Symbol("b");
let c = Symbol("c");

Object.defineProperties(obj, {
  [b]: {
    value: "cde val",
  },
  [c]: {
    value: "fff val",
  },
});

console.log(Object.getOwnPropertyDescriptors(obj));
/*{
  name: {
    value: 'wanmg',
    writable: true,
    enumerable: true,
    configurable: true
  },
  age: { value: 12, writable: true, enumerable: true, configurable: true },
  [Symbol(b)]: {
    value: 'cde val',
    writable: false,
    enumerable: false,
    configurable: false
  },
  [Symbol(c)]: {
    value: 'fff val',
    writable: false,
    enumerable: false,
    configurable: false
  }
}*/

Reflect.ownKeys():返回两种类型的键

js
let obj = {
  name: "wanmg",
  age: 12,
};
let b = Symbol("b");
let c = Symbol("c");

Object.defineProperties(obj, {
  [b]: {
    value: "cde val",
  },
  [c]: {
    value: "fff val",
  },
});

console.log(Reflect.ownKeys(obj));//[ 'name', 'age', Symbol(b), Symbol(c) ]

运算符

指数运算符 (**)

ECMAScript 7 中新增的

Math.pow(3,2)==3**2

加性运算符

加法:

1、加法运算符需要注意数据类型,可以进行字符串的加法运算。

2、两个字符串相加相当于两个字符串拼接到一起。其中有一个是字符串,相加后仍然是字符串。

3、如果一个是字符串,另一个是数值,对象或字符串,内部调用toString()方法将其转换为字符 串,在进行拼接。如果为null或undefined,则内部再调用String()方法,变为字符串‘null’和’undefined‘,然后再拼接。

相等操作符

等于和不等于在比较前会执行类型转换,全等和不全等不会进行类型转换,因此只有数值和类型都相等是才会返回true。

等于和不等于

规则:

  • 任意一个为布尔值,则将其转换为数值再进行比较,false为0,true为1
  • 一个为字符串,一个为数值,将字符串转换为数值后再进行比较。
  • 有一个为对象,则调用对象的valueOf()方法取得原始值,再进行比较。
  • null和undefined相等。
  • null和undefined不能转换为其他类型的值再进行比较。
  • 有一个为NaN,则返回false.
  • 如果两个都是对象,只有当指向同一个对象是才返回true.
结果表达式
truenull == undefined
false'NaN' == NaN
false5 == NaN
trueNaN != NaN
truefalse==0
truetrue == 1
falsetrue == 2
falseunndefined == 0
falsenull == 0
true"5" == 5

全等和不全等

只有当类型和数值都相等是才为true

undefined === null // false 类型不同所以为false

标签语句

label : statement

标签语句最常用的是搭配break和continue语句使用

js
 let num = 0;
        out:
            for (let i = 0; i < 10; i++) {
                for (let j = 0; j < 10; j++) {
                    if (i == 5 && j == 5) {
                        continue out;
                    }
                    num++;
                }

            }
		//当i==5和j==5时,跳到out,然后继续执行,所以只有55到60之间没有执行
        console.log(num);  // 95
js
 let num = 0;
        out:
            for (let i = 0; i < 10; i++) {
                for (let j = 0; j < 10; j++) {
                    if (i == 5 && j == 5) {
                        break out;
                    }
                    num++;
                }

            }
		//当i==5和j==5时,调到out,内外循环都停止了,所以就只执行到55
        console.log(num);  // 55

函数

函数的特点:

  1. 不需要指定函数的返回值,因为任何函数可以在任何时候返回任何值。
  2. 不指定返回值得函数实际上返回undefined.