完整的JavaScript实现由下列三个不同的部分组成:
- 核心(ECMAScript)
- 文档对象模型(DOM)
- 浏览器对象模型(BOM)
ECMAScript
是由EXMA-262定义的,它提供了核心语言功能。ECMA-262规定这门语言的下列组成部分:语法、类型、语句、关键字、保留字、操作符、对象。<script>
中定义了下列6个属性:
async
:可选,表示应该立即下载脚本,但不应妨碍页面中的其他操作。只对外部脚本文件有效charset
:可选,表示通过src属性指定的代码的字符集,比较少用。defer
:可选,表示脚本可以延迟到文档完全被解析和显示之后再执行。只对外部脚本文件有效。language
:已废弃src
:可选,表示包含要执行代码的外部文件type
:可选,表示编写代码使用的脚本语言的内容类型(也称为MIME类型)。在HTML5中,默认是text/javascript,所以不需要设置。
<script>
元素嵌入JavaScript代码,有两种方式:
<script>
元素之间:第二种:使用外链脚本形式,必须有src属性,而且指定一个外部JavaScript文件的链接。
<script src="example.js"></script>
好处
- 可维护性:将JavaScript文件都放在一个文件夹中,比每次都需要到不同的HTML页面修改JavaScript方便维护。
- 可缓存:浏览器会缓存所有外部JavaScript文件,所以当你有多个页面使用同一个JavaScript脚本时,这个脚本只需下载一次。
小结
- JavaScript由
ECMAScript
、DOM
、BOM
三部分组成; - ECMAScript由ECMA-262定义,提供核心语言功能;
- 文档对象模型(DOM),提供访问和操作网页内容的方法和接口;
- 浏览器对象模型(BOM),提供与浏览器交互的方法和接口;
- 把JavaScript插入到HTML页面中要使用
<script>
元素,可以内嵌,也可以外链文件; - 使用
defer
属性可以让脚本在文档完全呈现之后再执行,延迟脚本总是按照它们的顺序执行;
使用async
属性表示当前脚本不必等待其他脚本,也不必阻塞文档呈现,不能保证按照它们在页面中出现的顺序执行。 - 使用
<noscript>
元素可以指定在不支持脚本的浏览器中显示的提示内容。
1.2标识符是指变量、函数、属性的名字,或函数的参数。
标识符格式规则:
- 第一个字符必须是一个字母、下划线(
_
)或一个美元符号($
) - 其他字符可以是字母、下划线、美元符号或数字。
break do instanceof typeof
case else new var
catch finally return void
continue for switch while
debugger function this with
default if throw delete
in try
abstract enum int short
boolean export interface static
byte extends long super
char final native synchronized
class float package throws
const goto private transient
debugger implements protected volatile
double import public
如果在函数中使用var定义一个变量,那么这个变量在函数退出后就会被销毁。
function test(){
var name = 'tg'; //局部变量
}
test();
console.log(name); // 报错
所有变量的声明语句,都会被提升到代码的头部。
在函数内也一样,函数中的所有变量声明会在函数执行时被“提升”至函数体顶端。
console.log(a); // undefined
var a = 1;
function test(){
console.log(a); // undefined
var a = 2;
}
test();
var obj1 = new Object();
var obj2 = obj1;
obj2.name = 'tg';
console.log(obj1.name); // “tg"
换行符(\u000A)
回车符(\u000D)
行分隔符(\u2028)
段分隔符(\u2029)
四、JavaScript数据类型
Undefined
、Null
、Boolean
、Number
和String
。
Object
typeof
操作符用来检测给定变量的数据类型,可能的返回值:
"undefined" 这个值未定义
"boolean" 这个值是布尔值
"string" 这个值是字符串
"number" 这个值是数值
"object" 这个值是对象或null
"function" 这个值是函数
Null
类型也是只有一个值的数据类型,这个特殊值就是null
。null
值可以看作是一个空对象指针。
转换规则:
- 对于true或false,返回原值(true或false)
- 对于String类型的值,任何非空字符串返回true,空字符串("")返回false
- 对于Number类型的值,任何非零数字值(包括无穷大),返回true;0和NaN返回false
- 对于Object类型的值,任何对象返回true,null返回false
- 对于Undefined类型,undefined返回false(只有一个值)
浮点数值
指包含一个小数点,并且小数点后面必须至少有一个数字。
对于那些极大或极小的数值,我们可以使用科学计数法(e表示法)来表示浮点数值。
e表示法表示的数值等于e前面的数值乘以10的指数次幂:
var floatNum = 3.125e7; // 31250000
Infinity
值;如果这个值是负数,则会被转换为-Infinity
(负无穷)
isFinite()
来判断这个值是否无穷
isNaN()
函数来判断是否非数值。会尝试将这个值转换为数值,某些不是数值的值会直接转换为数值,比如:字符串"10"或Boolean值。而任何不能被转换为数值的值都会导致这个函数返回true。
- 任何涉及NaN的操作都会返回NaN。
- NaN与任何值都不相等,包括NaN本身。
4.4数值转换
有3个函数可以把非数值转换为数值:Number():用于任何数据类型
parseInt()
和parseFloat():用于字符串转成数值
Number()函数的转换规则:
- 如果是Boolean值,true和false将分别转换为1和0
- 如果是数字值,只是简单的传入和返回
- 如果是null值,返回0
- 如果是undefined,返回NaN
- 如果是字符串,遵循下列规则:
(
- 如果是字符串中只包含数字(包括前面带正负号),则将其转换为十进制数值(前导的零会被忽略)
- 如果字符串中包含有效的浮点格式,如1.1,则将其转换为对应的浮点数值
- 如果字符串中包含有效的十六进制,如0xf,则将其转换为相同大小的十进制数值
- 如果字符串是空的,返回0
- 如果字符串中包含上述格式以外的字符,返回NaN)
- 如果是对象,则调用对象的valueOf()方法,然后依照前面的规则转换返回的值。如果转换的结果是NaN,则调用对象的toString()方法,然后再次依照前面的规则转换返回字符串值
parseInt()
提供第二个参数,指定需要转换的进制。
console.log(parseInt('123tg')); // 123
console.log(parseInt('')); // NaN
console.log(parseInt('070')); // 70
console.log(parseInt('0xf')); //15
console.log(parseInt(22.5)); // 22
\n 换号
\t 制表
\b 空格
\r 回车
\f 进纸
\\ 斜杠
\' 单引号
\" 双引号
\xnn 以十六进制代码nn表示的一个字符(n为0~F),比如:\x41表示"A"
\unnn 以十六进制代码nnnn表示的一个Unicode字符(n为0~F)。比如:\u03a3表示Σ
- 使用每个值(null和undefined除外)都有的
toString()
方法
- 可以使用转型函数String(),能将任何类型的值转换为字符串,转换规则:
如果值有toString()方法,则调用该方法并返回相应的结果
如果值是null,则返回null
如果值是undefined,则返回undefined -
console.log(String(10)); // “10"
要把某个值转为字符串,还可以使用加号操作符:
console.log( true + ''); // "true”
6、Object类型
var o = new Object();
Object
的每个实例都具有下列属性和方法:
Constructor
:保存着用于创建当前对象的函数,比如上面的例子,构造函数就是Object()hasOwnProperty(propertyName)
:用于检查给定的属性在当前对象实例中是否存在(而不是在实例的原型中),参数必须是字符串形式isPrototypeOf(object)
:用于检查传入的对象是否是另一个对象的原型propertyIsEnumerable(propertyName)
:用于检查给定的属性是否能够使用for-in语句来枚举,参数必须是字符串形式toLocaleString()
:返回对象的字符串表示,该字符串与执行环境的地区对应toString()
:返回对象的字符串表valueOf()
:返回对象的字符串、数值或布尔值表示,通常和toString()返回的值相同
返回当前对象对应的值,默认情况下返回对象本身。
var o = {
name: 'tg',
age: 24
};
console.log(o == o.valueOf()); // true
var num = 2;
var age = (num++) + 2;
console.log(age); // 4
console.log(num); // 3
包含它们的语句是被求值之后才执行(先和其他值进行操作后,再自增或自减):
- 当操作数是一个包含有效数字字符的字符串,系统会将其转换为数字值,再执行递减或递增。
- 当操作数是一个不包含有效数字字符的字符串,系统将变量的值设置为NaN
- 当操作数是布尔值,会将其转为数值(true转为1,false转为0)再操作。
- 当操作数是浮点数值,直接执行递减或递增
- 当操作数是对象,先调用对象的valueOf()方法取得一个可供操作的值,然后再遵循上面的三条规则。如果结果是NaN,则在调用toString()方法后再遵循上面的规则转换。
按位非运算符(~)进行否运算
,执行按位非的结果就是返回数值的反码。
~ 3 // -4
//3的二进制码
00000000000000000000000000000011
// 取反码
11111111111111111111111111111100
//补码转为十进制的规则,在下面可以看到
11111111111111111111111111111011 //减1
00000000000000000000000000000100 //再次取反得到~3的十进制,也就是4,加上负号,就是-4
(2)按位与(AND)
0 & 3 //0
或运算
.0 | 3 // 3
使用按位异或(^)来进行异或运算
。
0 ^ 3 // 3
(5)左移
左移运算符(<<),这个运算符会将所有位向左移动指定的位数,尾部补0。
2 << 5 // 64
(6)右移
有符号的右移(>>)将数值向右移动,但保留符号位(即正负号标记,也就是第32位)
64 >> 5 // 2
无符号的右移(>>>),这个运算符会将数值的所有32位向右移动。对正数来说,无符号右移的结果与有符号右移相同:
64 >>> 5 //2
逻辑非规则:
- 如果操作数是一个对象、非空字符串、任意非0数值(包括Infinity),则返回false
- 如果操作数是空字符串、数值0、null、undefined、NaN,则返回true
逻辑与(&&)有两个操作数,如果是布尔值,只有两个都是true时,才会返回true,否则返回false
如果不是布尔值,它遵循下面的规则:
- 如果第一个操作数是对象,则返回第二个操作数
- 如果第二个操作数是对象,则只有在第一个操作数的求值为true时才会返回第二个操作数
- 如果有一个操作数是null,则返回null
- 如果有一个操作数是NaN,则返回NaN
- 如果有一个操作数是undefined,则返回undefined
如果两个操作数都是布尔值,则有一个为true时,就返回true,否则返回false。
如果有一个操作数不是布尔值,则遵循下列规则:
- 如果第一个操作数是对象,则返回第一个操作数
- 如果第一个操作数的求值结果是false,则返回第二个操作数
- 如果两个操作数都是对象,则返回第一个操作数
- 如果两个操作数都是null,则返回null
- 如果两个操作数都是NaN,则返回NaN
- 如果两个操作数都是undefined,则返回undefined
逻辑或也是短路运算符,也就是说,如果第一个操作数的求值结果为true,就不会对第二个操作数求值了。
处理特殊值时,乘法运算符会遵循下列规则:
- 如果操作数都是数值,但乘积超过了ECMAScript数值范围,则返回Infinity或-Infinity
- 如果有一个操作数是NaN,结果是NaN
- 如果是Infinity乘以0,结果是NaN
- 如果是Infinity与非0数值相乘,结果是Infinity或-Infinity,取决于非0数值的符号
- 如果是Infinity与Infinity相乘,结果是Infinity
- 如果有一个操作数不是数值,则在后台调用Number()将其转换为数值,然后遵循上面的规则
console.log(1 * NaN); // NaN
console.log( Infinity * 2); // Infinity
console.log(Infinity * 0); // NaN
console.log(Infinity * Infinity); // Infinity
(2)除法
处理特殊值,规则如下:
- 如果操作数都是数值,但商超过了ECMAScript的表示范围,则返回Infinity或-Infinity
- 如果有一个操作数是NaN,结果是NaN
- 如果是Infinity被Infinity除,结果是NaN
- 如果是零被零除,结果是NaN
- 如果是非零的有限数被零除,结果是Infinity或-Infinity,取决于有符号的操作数
- 如果是Infinity被任何非零数值除,结果是Infinity或-Infinity
- 如果有一个操作数不是数值,则在后台调用Number()将其转换为数值,然后遵循上面的规则。
console.log(NaN / 1); // NaN
console.log(0 / 0); // NaN
console.log(1 / 0); // Infinity
console.log(2 / Infinity); // 0
console.log(Infinity / Infinity); // NaN
console.log(Infinity / 2); // Infinity
(3)求模
求模(余数)运算符(%)
处理特殊值,规则如下:
- 如果被除数是无穷大值而除数是有限大的数值,结果是NaN
- 如果被除数是有限大的数值而除数是零,结果是NaN
- 如果是Infinity被Infinity除,结果是NaN
- 如果被除数是有限大的数值而除数是无穷大的数值,结果是被除数
- 如果被除数是零,结果是零
- 如果有一个操作数不是数值,则在后台调用Number()将其转换为数值,然后遵循上面的规则。
如果有一个操作数是字符串,则遵循下列规则:
- 如果两个操作数都是字符串,则拼接两个字符串
- 如果只有一个操作数是字符串,则将另一操作数转换为字符串,然后拼接
- 如果有一个操作数是对象、数值或布尔值,则调用它们的toString()方法取得相应的字符串值,然后遵循上面的规则。对于undefined和null,则分别调用String()函数并取得字符串"undefined"和”null"。
- 如果有一个操作数是字符串、布尔值、null或undefined,则先在后台调用Number()将其转换为数值,然后遵循上面的规则进行计算。
- 如果有一个操作数是对象,则调用对象的valueOf()方法以取得表示该对象的数值;如果该对象没有valueOf()方法,则调用其toString()方法将得到的字符串转换为数值,然后遵循上面的规则进行计算。
当使用了非数值时,则会遵循下列规则:
- 如果两个操作数是字符串,则比较两个字符串对应的字符编码值
- 如果一个操作数是数值,则将另一个操作数转换为一个数值,然后进行比较
- 如果一个操作数是对象,则调用这个对象的valueOf()方法,用得到的结果按照前面的规则比较。如果对象没有valueOf()方法,则调用toString()方法,并用得到的结果按照上面的规则进行比较。
- 如果一个操作数是布尔值,则先将其转换为数值,然后进行比较。
(7)相等运算符
相等运算符有两组:相等和不相等(先转换再比较)、全等和不全等(只比较不转换)
对于不同的数据类型,转换规则如下:
- 如果有一个操作数是布尔值,则在比较前先将其转换为数值(false转为0,true转为1)
- 如果一个操作数是字符串,另一个操作数是数值,先将字符串转为数值
- 如果一个操作数是对象,另一个不是,先调用对象的valueOf()方法,用得到的基本类型值按照前面的规则进行比较
- null和undefined是相等的
要比较之前,不能将null和undefined转换成其他任何值 - 如果有一个操作数是NaN,则相等运算符返回false,不相等运算符返回true。(要记住NaN不等于本身原则)
- 如果两个操作数都是对象,则比较它们是不是同一个对象。如果两个操作数都指向同一个对象,则相等运算符返回true,否则返回false。
NaN == NaN // false
true == 1 // true
null == undefined // true
'55' == 55 // true
'55' === 55 // false
var name = (1 > 2) ? 'tg' : 'tg2'; // “tg2"
使用逗号运算符可以在一条语句中执行多个操作:
var name = 'tg', age = 1;
逗号运算符还可以用于赋值。在用于赋值时,逗号运算符总会返回表达式中的最后一项:
var num = (1,5,3); // num的值为3
in运算符
in运算符希望它的左操作数是一个字符串或可以转换成为字符串,希望它的右操作数是一个对象。如果右侧的对象拥有一个名为左操作数值的属性名,则返回true。
var o = {x:1};
"x" in o //true
1.12 instanceof运算符
instanceof
运算符希望左操作数是一个对象,右操作数标识对象的类。如果左侧的对象是右侧类的实例,则表达式返回true。
var a = new Array();
a instanceof Object; //true
注意:所有对象都是Object的实例
1.13 typeof运算符
typeof
是一元运算符,用来判断数据类型:
typeof 1 // "number"
1.14 delete运算符
delete
是一元运算符,它用来删除对象的属性或数组元素。
var o={x:1}
delete o.x;
"x" in o //false
1.15 void运算符
void
是一元运算符,它出现在操作数之前,操作数可以是任意类型。操作数会照常计算,但忽略计算结果并返回undefined。
void 0 //undefined
void(0) //undefined
var a = 1;
void (a=2);
a //2
这个运算符主要是用于书签工具(bookmarklet),以及用于在超级链接中插入代码,目的是返回undefined可以防止网页跳转。
<a href="javascript:void(0)"></a>