JavaScript 正则表达式方法
什么是正则表达式?
正则表达式(Regular Expression,简称RegExp)是用于匹配字符串中字符组合的模式。在JavaScript中,正则表达式也是对象,这些模式被用于RegExp
的exec
和test
方法,以及String
的match
、matchAll
、replace
、replaceAll
、search
和split
方法。
正则表达式在处理文本验证、查找和替换等任务中特别有用,比如验证电子邮件格式、提取网页中的特定内容等。
创建正则表达式
在JavaScript中,有两种方式可以创建正则表达式:
1. 使用正则表达式字面量
const regex = /pattern/flags;
2. 使用RegExp构造函数
const regex = new RegExp('pattern', 'flags');
示例:
// 使用字面量创建
const regex1 = /hello/i;
// 使用构造函数创建
const regex2 = new RegExp('hello', 'i');
// 两者等价
console.log(regex1.test('Hello World')); // 输出: true
console.log(regex2.test('Hello World')); // 输出: true
正则表达式标志(flags)
标志用于修改正则表达式的行为:
g
:全局匹配,查找所有匹配项而非在找到第一个匹配后停止i
:忽略大小写m
:多行模式,使^
和$
匹配每一行的开头和结尾s
:使.
匹配包括换行符在内的所有字符u
:启用Unicode支持y
:粘性搜索,匹配从目标字符串的当前位置开始
RegExp对象方法
1. test()
test()
方法检测字符串中是否存在匹配正则表达式的模式,返回true
或false
。
语法:
regexObj.test(str)
示例:
const regex = /hello/i;
console.log(regex.test('Hello World')); // 输出: true
console.log(regex.test('Hi World')); // 输出: false
2. exec()
exec()
方法在字符串中执行查找匹配的操作,返回一个结果数组或null
。
语法:
regexObj.exec(str)
示例:
const regex = /(\d{3})-(\d{4})/;
const result = regex.exec('请联系123-4567获取更多信息');
console.log(result);
// 输出: ["123-4567", "123", "4567", index: 3, input: "请联系123-4567获取更多信息", groups: undefined]
console.log(result[0]); // 完整匹配: "123-4567"
console.log(result[1]); // 第一个捕获组: "123"
console.log(result[2]); // 第二个捕获组: "4567"
使用g
标志进行全局搜索:
const regex = /\d+/g;
let result;
const str = "有10个苹果和20个香蕉";
while ((result = regex.exec(str)) !== null) {
console.log(`找到 ${result[0]} 在位置 ${result.index}`);
}
// 输出:
// 找到 10 在位置 1
// 找到 20 在位置 7
String对象中的正则表达式方法
1. match()
match()
方法返回一个字符串匹配正则表达式的结果。
语法:
str.match(regexp)
示例:
// 不使用g标志
const str = "今天是2023年10月15日";
const regex = /\d+/;
console.log(str.match(regex));
// 输出: ["2023", index: 3, input: "今天是2023年10月15日", groups: undefined]
// 使用g标志
const regexGlobal = /\d+/g;
console.log(str.match(regexGlobal));
// 输出: ["2023", "10", "15"]
2. matchAll()
matchAll()
方法返回一个包含所有匹配正则表达式的结果及分组捕获组的迭代器。
语法:
str.matchAll(regexp)
示例:
const str = "今天是2023年10月15日";
const regex = /(\d+)([年月日])/g;
const matches = [...str.matchAll(regex)];
matches.forEach(match => {
console.log(`完整匹配: ${match[0]}`);
console.log(`数字: ${match[1]}`);
console.log(`单位: ${match[2]}`);
console.log('---');
});
// 输出:
// 完整匹配: 2023年
// 数字: 2023
// 单位: 年
// ---
// 完整匹配: 10月
// 数字: 10
// 单位: 月
// ---
// 完整匹配: 15日
// 数字: 15
// 单位: 日
// ---
3. search()
search()
方法执行正则表达式和字符串之间的搜索匹配,返回首个匹配项的索引,如未找到匹配项则返回-1。
语法:
str.search(regexp)
示例:
const str = "JavaScript是一门很流行的编程语言";
console.log(str.search(/编程/)); // 输出: 13
console.log(str.search(/Python/)); // 输出: -1
4. replace()
replace()
方法返回一个由替换值替换部分或所有的模式匹配项后的新字符串。
语法:
str.replace(regexp|substr, newSubstr|function)
示例:
// 基本替换
const str = "我喜欢苹果和香蕉";
console.log(str.replace(/苹果/, "橙子"));
// 输出: 我喜欢橙子和香蕉
// 全局替换
const text = "JavaScript是一门编程语言,JavaScript很简单";
console.log(text.replace(/JavaScript/g, "JS"));
// 输出: JS是一门编程语言,JS很简单
// 使用函数作为替换
function capitalizeFirstLetter(match) {
return match.charAt(0).toUpperCase() + match.slice(1);
}
const names = "john smith, jane doe, bob johnson";
console.log(names.replace(/\b[a-z]+\b/g, capitalizeFirstLetter));
// 输出: John Smith, Jane Doe, Bob Johnson
5. replaceAll()
replaceAll()
方法返回一个新字符串,其中所有匹配pattern
的部分都被replacement
替换。
语法:
str.replaceAll(regexp|substr, newSubstr|function)
示例:
const str = "苹果很好吃,苹果很健康";
console.log(str.replaceAll("苹果", "香蕉"));
// 输出: 香蕉很好吃,香蕉很健康
// 使用正则表达式(必须有g标志)
console.log(str.replaceAll(/苹果/g, "橙子"));
// 输出: 橙子很好吃,橙子很健康
6. split()
split()
方法使用指定的分隔符(可以是正则表达式)将一个字符串分割成子字符串数组。
语法:
str.split([separator[, limit]])
示例:
// 使用字符分割
const str = "苹果,香蕉,橙子";
console.log(str.split(","));
// 输出: ["苹果", "香蕉", "橙子"]
// 使用正则表达式分割
const dateStr = "2023-10-15";
console.log(dateStr.split(/-/));
// 输出: ["2023", "10", "15"]
// 分割并限制结果数量
const text = "a,b,c,d,e";
console.log(text.split(",", 3));
// 输出: ["a", "b", "c"]
// 使用更复杂的正则表达式
const complexStr = "苹果 香蕉,橙子;葡萄|西瓜";
console.log(complexStr.split(/[ ,;|]/));
// 输出: ["苹果", "香蕉", "橙子", "葡萄", "西瓜"]
实际应用案例
1. 表单验证
验证电子邮件地址:
function validateEmail(email) {
const regex = /^[^\s@]+@[^\s@]+\.[^\s@]+$/;
return regex.test(email);
}
console.log(validateEmail("user@example.com")); // 输出: true
console.log(validateEmail("invalid-email")); // 输出: false
验证手机号码(中国大陆):
function validatePhoneNumber(phone) {
const regex = /^1[3-9]\d{9}$/;
return regex.test(phone);
}
console.log(validatePhoneNumber("13812345678")); // 输出: true
console.log(validatePhoneNumber("1381234567")); // 输出: false (少一位)
2. 提取信息
从文本中提取所有URL:
function extractUrls(text) {
const urlRegex = /https?:\/\/[^\s]+/g;
return text.match(urlRegex) || [];
}
const article = "请访问 https://www.example.com 和 http://example.org 获取更多信息。";
console.log(extractUrls(article));
// 输出: ["https://www.example.com", "http://example.org"]
3. 格式化文本
将日期格式从 YYYY-MM-DD 转换为 DD/MM/YYYY:
function reformatDate(dateStr) {
return dateStr.replace(/(\d{4})-(\d{2})-(\d{2})/, "$3/$2/$1");
}
console.log(reformatDate("2023-10-15")); // 输出: "15/10/2023"
4. 高亮关键字
在文本中高亮搜索关键字:
function highlightKeyword(text, keyword) {
const regex = new RegExp(`(${keyword})`, 'gi');
return text.replace(regex, '<span style="background-color: yellow">$1</span>');
}
const paragraph = "JavaScript是一门强大的编程语言,javascript让网页更具交互性。";
const highlighted = highlightKeyword(paragraph, "javascript");
console.log(highlighted);
// 输出: "<span style="background-color: yellow">JavaScript</span>是一门强大的编程语言,<span style="background-color: yellow">javascript</span>让网页更具交互性。"
正则表达式模式
要充分利用正则表达式方法,了解一些常用的模式是很有帮助的:
基本字符匹配
.
- 匹配除了换行符之外的任何单个字符\d
- 匹配任何数字字符 (等同于[0-9]
)\D
- 匹配任何非数字字符 (等同于[^0-9]
)\w
- 匹配任何字母、数字或下划线 (等同于[A-Za-z0-9_]
)\W
- 匹配任何非字母、数字或下划线 (等同于[^A-Za-z0-9_]
)\s
- 匹配任何空白字符\S
- 匹配任何非空白字符
字符类
[abc]
- 匹配括号内的任何一个字符[^abc]
- 匹配除了括号内字符的任何字符[a-z]
- 匹配a到z范围内的任何字符
量词
*
- 匹配前面的表达式0次或多次+
- 匹配前面的表达式1次或多次?
- 匹配前面的表达式0次或1次{n}
- 精确匹配前面的表达式n次{n,}
- 匹配前面的表达式至少n次{n,m}
- 匹配前面的表达式n到m次
边界匹配
^
- 匹配字符串的开始$
- 匹配字符串的结束\b
- 匹配单词边界\B
- 匹配非单词边界
总结
在JavaScript中,正则表达式是处理字符串的强大工具。通过RegExp
对象的test()
和exec()
方法,以及字符串对象的match()
、matchAll()
、search()
、replace()
、replaceAll()
和split()
方法,我们可以执行各种字符串操作,如模式匹配、搜索、替换和分割。
正则表达式在开发中有广泛的应用,包括但不限于:
- 表单验证
- 数据提取
- 文本处理
- 格式转换
掌握正则表达式不仅能提高代码效率,还能减少手动处理字符串的繁琐工作。虽然正则表达式的语法可能看起来复杂,但通过实践和持续学习,你可以逐渐掌握这个强大的工具。
练习
- 编写一个函数,验证密码是否符合以下规则:至少8个字符,至少包含一个大写字母,一个小写字母和一个数字。
- 从一段文本中提取所有的电话号码(假设格式为XXX-XXX-XXXX)。
- 将文本中所有的日期从MM/DD/YYYY格式转换为YYYY-MM-DD格式。
- 编写一个函数,检测字符串是否是有效的URL。
正则表达式可能一开始看起来很复杂,但通过将它们分解成小片段并理解每个部分的功能,你可以逐渐掌握它们。在线正则表达式测试工具(如regex101.com)可以帮助你可视化地理解并测试你的正则表达式。
进一步学习资源
通过持续练习和应用,你将能够更有效地使用JavaScript正则表达式方法来解决各种字符串处理问题。