[JS]Javascript入门基础简介

本文深入浅出地介绍了JavaScript的基础知识,涵盖了变量声明、数据类型、数组、对象、函数、正则表达式等内容,帮助读者快速掌握这门流行脚本语言的核心概念。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >


JavaScript 是一门跨平台、面向对象的脚本语言:

  • 客户端的 JavaScript 通过提供对象,控制浏览器及其文档对象模型(DOM),来扩展语言核心。
  • 服务端的 JavaScript 则通过提供有关在服务器上运行 JavaScript 的对象来可扩展语言核心。

Javascript基础

JavaScript 是区分大小写的,并使用 Unicode 字符集。在 JavaScript 中,指令被称为语句 (Statement),并用分号(;)进行分隔。标识符必须以字母、下划线(_)或者美元符号($)开头;后续的字符也可以是数字(0-9)。

Javascript 注释的语法和 C++ 或许多其他语言类似:

  • // 单行注释
  • /* 这是一个更长的, 多行注释 */

声明

JavaScript有三种声明方式。

  • var:声明一个变量,可选初始化一个值。
  • let:声明一个块作用域的局部变量,可选初始化一个值。
  • const:声明一个块作用域的只读常量。

let非常适合用于 for循环内部的块级作用域。JS中的for循环体比较特殊,每次执行都是一个全新的独立的块作用域,用let声明的变量传入到 for循环体的作用域后,不会发生改变,不受外界的影响。

用 var 或 let 语句声明的变量,如果没有赋初始值,则其值为 undefined 。可以使用 undefined 来判断一个变量是否已赋值。

全局变量是全局对象的属性。在网页中,缺省的全局对象是 window ,所以可以用形如 window.variable 的语法来设置和访问全局变量。

数据类型

ECMAScript 标准定义了8种数据类型,七种基本数据类型和对象:

  • Boolean:布尔类型,分别是true 和 false。
  • null: 表明 null 值的特殊关键字。
  • undefined :表示变量未赋值时的属性的特殊关键字。
  • Number:整数或浮点数。
  • BigInt:任意精度的整数,可以安全地存储和操作大整数。
  • String:一串表示文本值的字符序列。
  • Symbol:( 在 ECMAScript 6 中新添加的类型),一种实例是唯一且不可改变的数据类型。
  • Object:所有自定义类型的基类。

检查 Object类型的合适方式是使用 instanceof 关键字。typeof 总是得到object类型。

数字

JavaScript 里面,数字均为双精度浮点类型,即一个介于 ± 2 − 1023 ±2^{−1023} ±21023 ± 2 + 1024 ±2^{+1024} ±2+1024之间的数字,或约为 ± 1 0 − 308 ±10^{−308} ±10308 ± 1 0 + 308 ±10^{+308} ±10+308,数字精度为53位。整数数值仅在 ± ( 2 53 − 1 ) ±(2^{53} - 1) ±(2531)的范围内可以表示准确。数字类型也还能表示三种符号值: +Infinity(正无穷)、-Infinity(负无穷)和 NaN (not-a-number,非数字)。J

JavaScript最近添加了 BigInt 的支持,能够用于表示极大的数字。使用 BigInt 的时候有一些注意事项,例如,不能让 BigInt 和 Number 直接进行运算,也不能用 Math 对象去操作 BigInt 数字。

数字的属性

属性描述
Number.MAX_VALUE可表示的最大值
Number.MIN_VALUE可表示的最小值
Number.NaN特指”非数字“
Number.NEGATIVE_INFINITY特指“负无穷”;在溢出时返回
Number.POSITIVE_INFINITY特指“正无穷”;在溢出时返回
Number.EPSILON表示1和比最接近1且大于1的最小Number之间的差别
Number.MIN_SAFE_INTEGERJavaScript最小安全整数.
Number.MAX_SAFE_INTEGERJavaScript最大安全整数.

数字的方法

方法描述
Number.parseFloat()把字符串参数解析成浮点数, 和全局方法 parseFloat() 作用一致.
Number.parseInt()把字符串解析成特定基数对应的整型数字,和全局方法 parseInt() 作用一致.
Number.isFinite()判断传递的值是否为有限数字。
Number.isInteger()判断传递的值是否为整数。
Number.isNaN()判断传递的值是否为 NaN. More robust version of the original global isNaN().
Number.isSafeInteger()判断传递的值是否为安全整数。

数字类型原型上的一些方法

方法描述
toExponential()返回一个数字的指数形式的字符串,形如:1.23e+2
toFixed()返回指定小数位数的表示形式,var a=123,b=a.toFixed(2)//b=“123.00”
toPrecision()返回一个指定精度的数字。如下例子中,a=123中,3会由于精度限制消失var a=123,b=a.toPrecision(2)//b=“1.2e+2”

字符串类型

JavaScript 的字符串类型用于表示文本数据。它是一组16位的无符号整数值的“元素”。在字符串中的每个元素占据了字符串的位置。第一个元素的索引为0。

String对象方法

方法描述
charAt, charCodeAt, codePointAt返回字符串指定位置的字符或者字符编码。
indexOf, lastIndexOf分别返回字符串中指定子串的位置或最后位置。
startsWith, endsWith, includes返回字符串是否以指定字符串开始、结束或包含指定字符串。
concat连接两个字符串并返回新的字符串。
fromCharCode, fromCodePoint从指定的Unicode值序列构造一个字符串。这是一个String类方法,不是实例方法。
split通过将字符串分离成一个个子串来把一个String对象分裂到一个字符串数组中。
slice从一个字符串提取片段并作为新字符串返回。
substring, substr分别通过指定起始和结束位置,起始位置和长度来返回字符串的指定子集。
match, replace, search通过正则表达式来工作.
toLowerCase, toUpperCase分别返回字符串的小写表示和大写表示。
normalize按照指定的一种 Unicode 正规形式将当前字符串正规化。
repeat将字符串内容重复指定次数后返回。
trim去掉字符串开头和结尾的空白字符。

集合

数组

数组(array)是一个有序的数据集合,我们可以通过数组名称(name)和索引(index)进行访问。
以下语句创建等效的数组:

var arr = new Array(element0, element1, ..., elementN);
var arr = Array(element0, element1, ..., elementN);
var arr = [element0, element1, ..., elementN];

在实施层面, JavaScript实际上是将元素作为标准的对象属性来存储,把数组索引作为属性名。长度属性是特殊的,它总是返回最后一个元素的索引值加1。

forEach() 方法提供了遍历数组元素的其他方法;被传递给forEach的函数会在数组的每个元素像上执行一次,元素作为参数传递给该函数。未赋值的值不会在forEach循环迭代。注意,在数组定义时省略的元素不会在forEach遍历时被列出,但是手动赋值为undefined的元素是会被列出的。通过for…in 循环来迭代数组将变得不明智,因为正常元素和所有可枚举的属性都会被列出。

相关方法

  • concat() 连接两个数组并返回一个新的数组。
  • join(deliminator = ‘,’) 将数组的所有元素连接成一个字符串。
  • push() 在数组末尾添加一个或多个元素,并返回数组操作后的长度。
  • pop() 从数组移出最后一个元素,并返回该元素。
  • shift() 从数组移出第一个元素,并返回该元素。
  • unshift() 在数组开头添加一个或多个元素,并返回数组的新长度。
  • slice(start_index, upto_index) 从数组提取一个片段,并作为一个新数组返回。
  • splice(index, count_to_remove, addElement1, addElement2, …)从数组移出一些元素,(可选)并替换它们。
  • reverse() 颠倒数组元素的顺序:第一个变成最后一个,最后一个变成第一个。
  • sort() 给数组元素排序。
  • indexOf(searchElement[, fromIndex]) 在数组中搜索searchElement 并返回第一个匹配的索引。
  • lastIndexOf(searchElement[, fromIndex]) 和 indexOf 差不多,但这是从结尾开始,并且是反向搜索。
  • forEach(callback[, thisObject]) 在数组每个元素项上执行callback。
  • map(callback[, thisObject]) 在数组的每个单元项上执行callback函数,并把返回包含回调函数返回值的新数组
  • filter(callback[, thisObject]) 返回一个包含所有在回调函数上返回为true的元素的新数组
  • every(callback[, thisObject]) 当数组中每一个元素在callback上被返回true时就返回true
  • some(callback[, thisObject]) 只要数组中有一项在callback上被返回true,就返回true
  • reduce(callback[, initialValue]) 使用回调函数 callback(firstValue, secondValue) 把数组列表计算成一个单一值
  • reduceRight(callback[, initalvalue]) 和 reduce()相似,但这从最后一个元素开始的。

Map对象

使用for…of循环来得到所有的[key, value]:

for (var [key, value] of sayings) {
  console.log(key + ' goes ' + value);
}

Object允许设置键值对、根据键获取值、删除键、检测某个键是否存在。而Map具有更多的优势。

  • Object的键均为Strings类型,在Map里键可以是任意类型。
  • 必须手动计算Object的尺寸,但是可以很容易地获取使用Map的尺寸。
  • Map的遍历遵循元素的插入顺序。
  • Object有原型,所以映射中有一些缺省的键(可以用 map = Object.create(null) 回避)。

三条决定用Map还是Object提示:

  • 如果键在运行时才能知道,或者所有的键类型相同,所有的值类型相同,那就使用Map。
  • 如果需要将原始值存储为键,则使用Map,因为Object将每个键视为字符串,不管它是一个数字值、布尔值还是任何其他原始值。
  • 如果需要对个别元素进行操作,使用Object。

WeakMap对象也是键值对的集合。它的键必须是对象类型,值可以是任意类型。它的键被弱保持,也就是说,当其键所指对象没有其他地方引用的时候,它会被GC回收掉。WeakMap提供的接口与Map相同。

与Map对象不同的是,WeakMap的键是不可枚举的。不提供列出其键的方法。列表是否存在取决于垃圾回收器的状态,是不可预知的。

Set对象

Set对象是一组值的集合,这些值是不重复的,可以按照添加顺序来遍历。

可以使用Array.from或展开操作符来完成集合到数组的转换。同样,Set的构造器接受数组作为参数,可以完成从Array到Set的转换。需要重申的是,Set对象中的值不重复,所以数组转换为集合时,所有重复值将会被删除。

Array.from(mySet);
[...mySet2];
mySet2 = new Set([1,2,3,4]);

Map的键和Set的值的等值判断都:

  • 判断使用与===相似的规则。
  • -0和+0相等。
  • NaN与自身相等(与===有所不同)。

解构

解构赋值语法是一个能从数组或对象对应的数组结构或对象字面量里提取数据的:

var foo = ["one", "two", "three"];
// 不使用解构
var one   = foo[0];
var two   = foo[1];
var three = foo[2];
// 使用解构
var [one, two, three] = foo;

从一个对象中结构时,若对应的属性不存在,则变量设为undefined。

比较

JavaScript提供三种不同的值比较操作:

  • 严格相等比较,使用 === :两个被比较的值在比较前都不进行隐式转换
    • 如果两个被比较的值具有不同的类型,这两个值是不等的。
    • 如果两个被比较的值类型相同,值也相同,并且都不是 number 类型时,两个值相等。
    • 如果两个值都是 number 类型,且不是 NaN,并且数值相同,两个值相等。
    • 如果两个值都是 number 类型,分别为 +0 和 -0 时,两个值相等。
    • 等式 (x !== x) 成立的唯一情况是 x 的值为 NaN。
  • 抽象相等比较,使用 ==:在比较前将两个被比较的值转换为相同类型。在转换后(等式的一边或两边都可能被转换),最终的比较方式等同于全等操作符 === 的比较方式。
  • Object.is:除Object.is(NaN,NaN)为 true,Object.is(+0,-0)为false外,其他与三等相同。
xy=====Object.is
undefinedundefinedtruetruetrue
nullnulltruetruetrue
truetruetruetruetrue
falsefalsetruetruetrue
"foo""foo"truetruetrue
00truetruetrue
+0-0truetruefalse
0falsetruefalsefalse
""falsetruefalsefalse
""0truefalsefalse
"0"0truefalsefalse
"17"17truefalsefalse
[1,2]"1,2"truefalsefalse
new String("foo")"foo"truefalsefalse
nullundefinedtruefalsefalse
nullfalsefalsefalsefalse
undefinedfalsefalsefalsefalse
{ foo: "bar" }{ foo: "bar" }falsefalsefalse
new String("foo")new String("foo")falsefalsefalse
0nullfalsefalsefalse
0NaNfalsefalsefalse
"foo"NaNfalsefalsefalse
NaNNaNfalsefalsetrue

操作符

delete

delete操作符,删除一个对象的属性或者一个数组中某一个键值。

delete 删除数组中的一个元素,这个元素就不在数组中了。例如,trees[3]被删除,trees[3] 仍然可寻址并返回undefined。

typeof

typeof 操作符返回一个表示 operand 类型的字符串值。

  • typeof operand
  • typeof (operand)

in

in操作符,如果所指定的属性确实存在于所指定的对象中,则会返回true:

propNameOrNumber in objectName

在这里 propNameOrNumber可以是一个代表着属性名的字符串或者是一个代表着数组索引的数值表达式(不能用于判断值是否在数组中),而objectName则是一个对象名。

instanceof

instanceof 如果所判别的对象确实是所指定的类型,则返回true。
objectName instanceof objectType

new

使用new operator 创建一个自定义类型或者是预置类型的对象实例。
super 关键字可以用来调用一个对象父类的函数,它在用来调用一个类的父类的构造函数时非常有用

字面值

数组字面值

数组字面值是一个封闭在方括号对([])中的包含有零个或多个表达式的列表,其中每个表达式代表数组的一个元素。当你使用数组字面值创建一个数组时,该数组将会以指定的值作为其元素进行初始化,而其长度被设定为元素的个数。

同一行中连写两个逗号(,),数组中就会产生一个没有被指定的元素,其初始值是undefined。元素列表的尾部添加了一个逗号,它将会被忽略。

对象字面值

对象字面值是封闭在花括号对({})中的一个对象的零个或多个"属性名-值"对的(元素)列表。可以使用数字或字符串字面值作为属性的名字,或者在另一个字面值内嵌套上一个字面值。对象属性名字可以是任意字符串,包括空串。如果对象属性名字不是合法的javascript标识符,它必须用""包裹。属性的名字不合法,那么便不能用.访问属性值,而是通过类数组标记([])访问和赋值。
var car = { manyCars: {a: "Saab", "b": "Jeep"}, 7: "Mazda" };

RegExp 字面值

RegExp 字面值 一个正则表达式是字符被斜线(正斜杠/)围成的表达式。
var re = /ab+c/;

模板字面量

模板字面量 template literals,使用反引号包括,可以通过${}引用变量,以及包含多行文本。

`Hello ${name}, how are you ${time}?`

语句

if语句

if…else 语句

if (condition_1) {
  statement_1;
}else if (condition_2) {
  statement_2;
}else {
  statement_last;
}

下面这些值将被计算出 false :

  • false
  • undefined
  • null
  • 0
  • NaN
  • 空字符串("")

注意:

var b = new Boolean(false);
if (b) //结果视为真
if(b==false) // 结果也视为真

switch语句

switch 语句

switch (expression) {
   case label_1:
      statements_1
      [break;]
   case label_2:
      statements_2
      [break;]
   ...
   default:
      statements_def
      [break;]
}

循环语句

JS中有这些循环语句:

  • for 语句
  • do…while 语句
  • while 语句
  • label 语句
  • break 语句
  • continue 语句
  • for…in 语句
  • for…of 语句
for ([initialExpression]; [condition]; [incrementExpression])
  statement

label示例

var num = 0;
outPoint:
for (var i = 0 ; i < 10 ; i++){
  for (var j = 0 ; j < 10 ; j++){
    if( i == 5 && j == 5 ){
      break outPoint; // 在 i = 5,j = 5 时,跳出所有循环,
                      // 返回到整个 outPoint 下方,继续执行
    }
    num++;
  }
}
alert(num); // 输出 55

for…in 语句循环一个指定的变量来循环一个对象所有可枚举的属性。JavaScript 会为每一个不同的属性执行指定的语句。

for (variable in object) {
  statements
}

for…of 语句在可迭代对象(包括Array、Map、Set、arguments 等等)上创建了一个循环,对值的每一个独特属性调用一次迭代。

for (variable of object) {
  statement
}

for…in 循环遍历的结果是数组元素的下标,而 for…of 遍历的结果是元素的值:

let arr = [3, 5, 7];
arr.foo = "hello";

for (let i in arr) {
   console.log(i); // 输出 "0", "1", "2", "foo"
}

for (let i of arr) {
   console.log(i); // 输出 "3", "5", "7"
}

异常语句

throw 语句throw expression;可以抛出任意表达式而不是特定一种类型的表达式

try…catch 语句

try { // statements to try
  monthName = getMonthName(myMonth); // function could throw exception
}
catch (e) {
  monthName = "unknown";
  logMyErrors(e); // pass exception object to error handler -> your own function
}

finally块包含了在try和catch块完成后执行的语句。finally块无论是否抛出异常都会执行。

扩展语句(…)

扩展语句符允许一个表达式在原地展开, 当需要多个参数 (比如函数调用时) 或者多个值(比如字面量数组) 。

var parts = ['shoulder', 'knees'];
var lyrics = ['head', ...parts, 'and', 'toes'];

function f(x, y, z) { }
var args = [0, 1, 2];
f(...args);

函数

函数是 JavaScript 中的基本组件之一。一个JavaScript 函数用function关键字定义,后面跟着函数名和圆括号。在JavaScript中,函数参数的默认值是undefined。剩余参数语法允许将不确定数量的参数表示为数组。

function multiply(multiplier, ...theArgs) {
  return theArgs.map(x => multiplier * x);
}

var arr = multiply(2, 1, 2, 3);
console.log(arr); // [2, 4, 6]

箭头函数表达式(也称胖箭头函数)相比函数表达式具有较短的语法并以词法的方式绑定 this(箭头函数捕捉闭包上下文的this值)。箭头函数总是匿名的。

闭包让你可以在一个内层函数中访问到其外层函数的作用域。在 JavaScript 中,每当创建一个函数,闭包就会在函数创建的同时被创建出来。

内建函数

JavaScript语言有好些顶级的内建函数:

  • eval()方法会对一串字符串形式的JavaScript代码字符求值。
  • uneval()方法创建的一个Object的源代码的字符串表示。
  • isFinite()函数判断传入的值是否是有限的数值。 如果需要的话,其参数首先被转换为一个数值。
  • isNaN()函数判断一个值是否是NaN。注意:isNaN函数内部的强制转换规则十分有趣; 另一个可供选择的是ECMAScript 6 中定义Number.isNaN() , 或者使用 typeof来判断数值类型。
  • parseFloat() 函数解析字符串参数,并返回一个浮点数。
  • parseInt() 函数解析字符串参数,并返回指定的基数(基础数学中的数制)的整数。
  • decodeURI() 函数对先前经过encodeURI函数或者其他类似方法编码过的字符串进行解码。
  • decodeURIComponent()方法对先前经过encodeURIComponent函数或者其他类似方法编码过的字符串进行解码。
  • encodeURI()方法通过用以一个,两个,三个或四个转义序列表示字符的UTF-8编码替换统一资源标识符(URI)的某些字符来进行编码(每个字符对应四个转义序列,这四个序列组了两个”替代“字符)。
  • encodeURIComponent() 方法通过用以一个,两个,三个或四个转义序列表示字符的UTF-8编码替换统一资源标识符(URI)的每个字符来进行编码(每个字符对应四个转义序列,这四个序列组了两个”替代“字符)。

对象

JavaScript是一种基于原型而不是基于类的基于对象(object-based)语言。基于原型的语言具有所谓原型对象(prototypical object)的概念。原型对象可以作为一个模板,新对象可以从中获得原始的属性。任何对象都可以指定其自身的属性,既可以是创建时也可以在运行时创建。而且,任何对象都可以作为另一个对象的原型(prototype),从而允许后者共享前者的属性。

在 JavaScript 中,允许运行时添加或者移除任何对象的属性。如果您为一个对象中添加了一个属性,而这个对象又作为其它对象的原型,则以该对象作为原型的所有其它对象也将获得该属性。
基于类(Java)和基于原型(JavaScript)的对象系统的比较 :

基于类的(Java)基于原型的(JavaScript)
类和实例是不同的事物。所有对象均为实例。
通过类定义来定义类;通过构造器方法来实例化类。通过构造器函数来定义和创建一组对象。
通过 new 操作符创建单个对象。相同。
通过类定义来定义现存类的子类,从而构建对象的层级结构。指定一个对象作为原型并且与构造函数一起构建对象的层级结构
遵循类链继承属性。遵循原型链继承属性。
类定义指定类的所有实例的所有属性。无法在运行时动态添加属性。构造器函数或原型指定实例的初始属性集。允许动态地向单个的对象或者整个对象集中添加或移除属性。

一个对象就是一系列属性的集合,一个属性包含一个名和一个值。一个属性的值可以是函数,这种情况下属性也被称为方法。对象中未赋值的属性的值为undefined。JavaScript 对象的属性也可以通过方括号访问或者设置, 对象有时也被叫作关联数组, 因为每个属性都有一个用于访问它的字符串值。一个对象的属性名可以是任何有效的 JavaScript 字符串,或者可以被转换为字符串的任何类型,包括空字符串。然而,一个属性的名称如果不是一个有效的 JavaScript 标识符(例如,一个由空格或连字符,或者以数字开头的属性名),就只能通过方括号标记访问(方括号中的所有键都将转换为字符串类型,)。这个标记法在属性名称是动态判定(属性名只有到运行时才能判定)时非常有用。

可以在 for…in 语句中使用方括号标记以枚举一个对象的所有属性。

有三种原生的方法用于列出或枚举对象的属性:

  • for…in 循环:该方法依次访问一个对象及其原型链中所有可枚举的属性。
  • Object.keys(o):该方法返回对象 o 自身包含(不包括原型中)的所有可枚举属性的名称的数组。
  • Object.getOwnPropertyNames(o):该方法返回对象 o 自身包含(不包括原型中)的所有属性(无论是否可枚举)的名称的数组。

在访问一个对象的属性时,JavaScript 将执行下面的步骤:

  • 检查对象自身是否存在。如果存在,返回值。
  • 如果本地值不存在,检查原型链(通过 proto 属性)。
  • 如果原型链中的某个对象具有指定属性,则返回值。
  • 如果这样的属性不存在,则对象没有该属性,返回 undefined。

Promise 对象

Promise 是一个对象,它代表了一个异步操作的最终完成或者失败。本质上 Promise 是一个函数返回的对象,可以在它上面绑定回调函数,这样就不需要在一开始把回调函数作为参数传入这个函数了。

Promise 对象有以下几种状态:

  • pending:初始的状态,即正在执行,不处于 fulfilled 或 rejected 状态。
  • fulfilled:成功的完成了操作。
  • rejected:失败,没有完成操作。
  • settled:Promise 处于 fulfilled 或 rejected 二者中的任意一个状态, 不会是 pending。

在使用 Promise 时,会有以下约定:

  • 在本轮 事件循环 运行完成之前,回调函数是不会被调用的。
  • 即使异步操作已经完成(成功或失败),在这之后通过 then() 添加的回调函数也会被调用。
  • 通过多次调用 then() 可以添加多个回调函数,它们会按照插入顺序进行执行。

迭代器是一个对象,它定义一个序列,并在终止时可能返回一个返回值。 更具体地说,迭代器是通过使用 next() 方法实现 Iterator protocol 的任何一个对象,该方法返回具有两个属性的对象:

  • value,这是序列中的 next 值;
  • done ,如果已经迭代到序列中的最后一个值,则它为 true 。
  • 在产生终止值之后,对next()的额外调用应该继续返回{done:true}。

为了实现可迭代,一个对象必须实现 @@iterator 方法,这意味着这个对象(或其原型链中的任意一个对象)必须具有一个带 Symbol.iterator 键(key)的属性。

modules 模块

JavaScript 模块依赖于import和 export。export要放在最外层;能够导出函数,var,let,const, 和类。一个更方便的方法导出所有你想要导出的模块的方法是在模块文件的末尾使用一个export 语句, 语句是用花括号括起来的用逗号分割的列表。比如:
export { name, draw, reportArea, reportPerimeter };

在 import 和 export 语句的大括号中,可以使用 as 关键字跟一个新的名字,来改变在顶级模块中将要使用的功能的标识名字。
import * as Module from '/modules/module.mjs';

正则表达式

正则表达式是用于匹配字符串中字符组合的模式。

创建一个正则表达式可以:

// 字面量方式
var re = /ab+c/;

// 构造函数方式
var re = new RegExp("ab+c");

正则表达式中的特殊字符

字符含义
\依照下列规则匹配:在非特殊字符之前的反斜杠表示下一个字符是特殊字符,不能按照字面理解。例如,前面没有 “” 的 “b” 通常匹配小写字母 “b”,即字符会被作为字面理解,无论它出现在哪里。但如果前面加了 “”,它将不再匹配任何字符,而是表示一个字符边界。在特殊字符之前的反斜杠表示下一个字符不是特殊字符,应该按照字面理解。详情请参阅下文中的 “转义(Escaping)” 部分。如果你想将字符串传递给 RegExp 构造函数,不要忘记在字符串字面量中反斜杠是转义字符。所以为了在模式中添加一个反斜杠,你需要在字符串字面量中转义它。/[a-z]\s/inew RegExp("[a-z]\\s", "i") 创建了相同的正则表达式:一个用于搜索后面紧跟着空白字符(\s 可看后文)并且在 a-z 范围内的任意字符的表达式。为了通过字符串字面量给 RegExp 构造函数创建包含反斜杠的表达式,你需要在字符串级别和正则表达式级别都对它进行转义。例如 /[a-z]:\\/inew RegExp("[a-z]:\\\\","i") 会创建相同的表达式,即匹配类似 “C:” 字符串。
^匹配输入的开始。如果多行标志被设置为 true,那么也匹配换行符后紧跟的位置。例如,/^A/ 并不会匹配 “an A” 中的 ‘A’,但是会匹配 “An E” 中的 ‘A’。当 ‘^’ 作为第一个字符出现在一个字符集合模式时,它将会有不同的含义。反向字符集合 一节有详细介绍和示例。
$匹配输入的结束。如果多行标志被设置为 true,那么也匹配换行符前的位置。例如,/t$/ 并不会匹配 “eater” 中的 ‘t’,但是会匹配 “eat” 中的 ‘t’。
*匹配前一个表达式 0 次或多次。等价于 {0,}。例如,/bo*/ 会匹配 “A ghost boooooed” 中的 ‘booooo’ 和 “A bird warbled” 中的 ‘b’,但是在 “A goat grunted” 中不会匹配任何内容。
+匹配前面一个表达式 1 次或者多次。等价于 {1,}。例如,/a+/ 会匹配 “candy” 中的 ‘a’ 和 “caaaaaaandy” 中所有的 ‘a’,但是在 “cndy” 中不会匹配任何内容。
?匹配前面一个表达式 0 次或者 1 次。等价于 {0,1}。例如,/e?le?/ 匹配 “angel” 中的 ‘el’、“angle” 中的 ‘le’ 以及 "oslo’ 中的 ‘l’。如果紧跟在任何量词 *、 +、? 或 {} 的后面,将会使量词变为非贪婪(匹配尽量少的字符),和缺省使用的贪婪模式(匹配尽可能多的字符)正好相反。例如,对 “123abc” 使用 /\d+/ 将会匹配 “123”,而使用 /\d+?/ 则只会匹配到 “1”。还用于先行断言中,如本表的 x(?=y)x(?!y) 条目所述。
.(小数点)默认匹配除换行符之外的任何单个字符。例如,/.n/ 将会匹配 “nay, an apple is on the tree” 中的 ‘an’ 和 ‘on’,但是不会匹配 ‘nay’。如果 s (“dotAll”) 标志位被设为 true,它也会匹配换行符。
(x)像下面的例子展示的那样,它会匹配 ‘x’ 并且记住匹配项。其中括号被称为捕获括号。模式 /(foo) (bar) \1 \2/ 中的 ‘(foo)’ 和 ‘(bar)’ 匹配并记住字符串 “foo bar foo bar” 中前两个单词。模式中的 \1\2 表示第一个和第二个被捕获括号匹配的子字符串,即 foobar,匹配了原字符串中的后两个单词。注意 \1\2、…、\n 是用在正则表达式的匹配环节,详情可以参阅后文的 \n 条目。而在正则表达式的替换环节,则要使用像 $1$2、…、$n 这样的语法,例如,'bar foo'.replace(/(...) (...)/, '$2 $1')$& 表示整个用于匹配的原字符串。
(?:x)匹配 ‘x’ 但是不记住匹配项。这种括号叫作非捕获括号,使得你能够定义与正则表达式运算符一起使用的子表达式。看看这个例子 /(?:foo){1,2}/。如果表达式是 /foo{1,2}/{1,2} 将只应用于 ‘foo’ 的最后一个字符 ‘o’。如果使用非捕获括号,则 {1,2} 会应用于整个 ‘foo’ 单词。更多信息,可以参阅下文的 Using parentheses 条目.
x(?=y)匹配’x’仅仅当’x’后面跟着’y’.这种叫做先行断言。例如,/Jack(?=Sprat)/会匹配到’Jack’仅当它后面跟着’Sprat’。/Jack(?=Sprat|Frost)/匹配‘Jack’仅当它后面跟着’Sprat’或者是‘Frost’。但是‘Sprat’和‘Frost’都不是匹配结果的一部分。
(?<=y)x匹配’x’仅当’x’前面是’y’.这种叫做后行断言。例如,/(?<=Jack)Sprat/会匹配到’ Sprat ‘仅仅当它前面是’ Jack '。/(?<=Jack|Tom)Sprat/匹配‘ Sprat ’仅仅当它前面是’Jack’或者是‘Tom’。但是‘Jack’和‘Tom’都不是匹配结果的一部分。
x(?!y)仅仅当’x’后面不跟着’y’时匹配’x’,这被称为正向否定查找。例如,仅仅当这个数字后面没有跟小数点的时候,/\d+(?!.)/ 匹配一个数字。正则表达式/\d+(?!.)/.exec(“3.141”)匹配‘141’而不是‘3.141’
(?<!*y*)*x*仅仅当’x’前面不是’y’时匹配’x’,这被称为反向否定查找。例如, 仅仅当这个数字前面没有负号的时候,/(?<!-)\d+/ 匹配一个数字。 /(?<!-)\d+/.exec('3') 匹配到 “3”. /(?<!-)\d+/.exec('-3') 因为这个数字前有负号,所以没有匹配到。
x|y匹配‘x’或者‘y’。例如,/green|red/匹配“green apple”中的‘green’和“red apple”中的‘red’
{n}n 是一个正整数,匹配了前面一个字符刚好出现了 n 次。 比如, /a{2}/ 不会匹配“candy”中的’a’,但是会匹配“caandy”中所有的 a,以及“caaandy”中的前两个’a’。
{n,}n是一个正整数,匹配前一个字符至少出现了n次。例如, /a{2,}/ 匹配 “aa”, “aaaa” 和 “aaaaa” 但是不匹配 “a”。
{n,m}n 和 m 都是整数。匹配前面的字符至少n次,最多m次。如果 n 或者 m 的值是0, 这个值被忽略。例如,/a{1, 3}/ 并不匹配“cndy”中的任意字符,匹配“candy”中的a,匹配“caandy”中的前两个a,也匹配“caaaaaaandy”中的前三个a。注意,当匹配”caaaaaaandy“时,匹配的值是“aaa”,即使原始的字符串中有更多的a。
[xyz\]一个字符集合。匹配方括号中的任意字符,包括转义序列。你可以使用破折号(-)来指定一个字符范围。对于点(.)和星号(*)这样的特殊符号在一个字符集中没有特殊的意义。他们不必进行转义,不过转义也是起作用的。 例如,[abcd] 和[a-d]是一样的。他们都匹配"brisket"中的‘b’,也都匹配“city”中的‘c’。/[a-z.]+/ 和/[\w.]+/与字符串“test.i.ng”匹配。
[^xyz\]一个反向字符集。也就是说, 它匹配任何没有包含在方括号中的字符。你可以使用破折号(-)来指定一个字符范围。任何普通字符在这里都是起作用的。例如,[^abc] 和 [^a-c] 是一样的。他们匹配"brisket"中的‘r’,也匹配“chop”中的‘h’。
[\b\]匹配一个退格(U+0008)。(不要和\b混淆了。)
\b匹配一个词的边界。一个词的边界就是一个词不被另外一个“字”字符跟随的位置或者前面跟其他“字”字符的位置,例如在字母和空格之间。注意,匹配中不包括匹配的字边界。换句话说,一个匹配的词的边界的内容的长度是0。(不要和[\b]混淆了)使用"moon"举例: /\bm/匹配“moon”中的‘m’; /oo\b/并不匹配"moon"中的’oo’,因为’oo’被一个“字”字符’n’紧跟着。 /oon\b/匹配"moon"中的’oon’,因为’oon’是这个字符串的结束部分。这样他没有被一个“字”字符紧跟着。 /\w\b\w/将不能匹配任何字符串,因为在一个单词中间的字符永远也不可能同时满足没有“字”字符跟随和有“字”字符跟随两种情况。注意: JavaScript的正则表达式引擎将特定的字符集定义为“字”字符。不在该集合中的任何字符都被认为是一个断词。这组字符相当有限:它只包括大写和小写的罗马字母,十进制数字和下划线字符。不幸的是,重要的字符,例如“é”或“ü”,被视为断词。
\B匹配一个非单词边界。匹配如下几种情况:字符串第一个字符为非“字”字符字符串最后一个字符为非“字”字符两个单词字符之间两个非单词字符之间空字符串例如,/\B…/匹配"noonday"中的’oo’, 而/y\B…/匹配"possibly yesterday"中的’yes‘
\c*X*当X是处于A到Z之间的字符的时候,匹配字符串中的一个控制符。例如,/\cM/ 匹配字符串中的 control-M (U+000D)。
\d匹配一个数字。``等价于[0-9]。例如, /\d/ 或者 /[0-9]/ 匹配"B2 is the suite number."中的’2’。
\D匹配一个非数字字符。``等价于[^0-9]。例如, /\D/ 或者 /[^0-9]/ 匹配"B2 is the suite number."中的’B’ 。
\f匹配一个换页符 (U+000C)。
\n匹配一个换行符 (U+000A)。
\r匹配一个回车符 (U+000D)。
\s匹配一个空白字符,包括空格、制表符、换页符和换行符。等价于[ \f\n\r\t\v\u00a0\u1680\u180e\u2000-\u200a\u2028\u2029\u202f\u205f\u3000\ufeff]。例如, /\s\w*/ 匹配"foo bar.“中的’ bar’。经测试,\s不匹配”\u180e",在当前版本Chrome(v80.0.3987.122)和Firefox(76.0.1)控制台输入/\s/.test("\u180e")均返回false。
\S匹配一个非空白字符。等价于 [^\f\n\r\t\v\u00a0\u1680\u180e\u2000-\u200a\u2028\u2029\u202f\u205f\u3000\ufeff]。例如,/\S\w*/ 匹配"foo bar."中的’foo’。
\t匹配一个水平制表符 (U+0009)。
\v匹配一个垂直制表符 (U+000B)。
\w匹配一个单字字符(字母、数字或者下划线)。等价于 [A-Za-z0-9_]。例如, /\w/ 匹配 “apple,” 中的 ‘a’,"$5.28,"中的 ‘5’ 和 “3D.” 中的 ‘3’。
\W匹配一个非单字字符。等价于 [^A-Za-z0-9_]。例如, /\W/ 或者 /[^A-Za-z0-9_]/ 匹配 “50%.” 中的 ‘%’。
\*n*在正则表达式中,它返回最后的第n个子捕获匹配的子字符串(捕获的数目以左括号计数)。比如 /apple(,)\sorange\1/ 匹配"apple, orange, cherry, peach."中的’apple, orange,’ 。
\0匹配 NULL(U+0000)字符, 不要在这后面跟其它小数,因为 \0<digits> 是一个八进制转义序列。
\xhh匹配一个两位十六进制数(\x00-\xFF)表示的字符。
\uhhhh匹配一个四位十六进制数表示的 UTF-16 代码单元。
\u{hhhh}或\u{hhhhh}(仅当设置了u标志时)匹配一个十六进制数表示的 Unicode 字符。

使用正则表达式的方法

方法描述
exec一个在字符串中执行查找匹配的RegExp方法,它返回一个数组(未匹配到则返回 null)。
test一个在字符串中测试是否匹配的RegExp方法,它返回 true 或 false。
match一个在字符串中执行查找匹配的String方法,它返回一个数组,在未匹配到时会返回 null。
matchAll一个在字符串中执行查找所有匹配的String方法,它返回一个迭代器(iterator)。
search一个在字符串中测试匹配的String方法,它返回匹配到的位置索引,或者在失败时返回-1。
replace一个在字符串中执行查找匹配的String方法,并且使用替换字符串替换掉匹配到的子字符串。
split一个使用正则表达式或者一个固定字符串分隔一个字符串,并将分隔后的子字符串存储到数组中的 String 方法。

正则表达式标志

标志描述
g全局搜索。
i不区分大小写搜索。
m多行搜索。
s允许 . 匹配换行符。
u使用unicode码的模式进行匹配。
y执行“粘性(sticky)”搜索,匹配从目标字符串的当前位置开始。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值