目录
- 一、实战入门:手机号正则校验案例
-
- [1.1 功能需求](#1.1 功能需求)
- [1.2 编码设计原则](#1.2 编码设计原则)
- [1.3 正则拆解与落地代码](#1.3 正则拆解与落地代码)
- 二、正则表达式基础语法
-
- [2.1 正则基础概念](#2.1 正则基础概念)
- [2.2 两个核心实例方法](#2.2 两个核心实例方法)
- [2.3 g全局修饰符](#2.3 g全局修饰符)
- 三、JS基础:两大数据类型体系
-
- [3.1 基本数据类型(值类型)](#3.1 基本数据类型(值类型))
- [3.2 引用数据类型(引用类型)](#3.2 引用数据类型(引用类型))
- 四、正则搭配字符串三大实战场景
-
- [4.1 场景1:提取文本中全部数字](#4.1 场景1:提取文本中全部数字)
- [4.2 场景2:短横线命名转为驼峰命名](#4.2 场景2:短横线命名转为驼峰命名)
- [4.3 场景3:递归实现简易模板渲染](#4.3 场景3:递归实现简易模板渲染)
- 五、全文总结&知识点复盘&避坑指南
一、实战入门:手机号正则校验案例
1.1 功能需求
编写正则表达式校验国内手机号码,约束规则:
- 整体严格11位纯数字;
- 首位固定为数字
1; - 第二位不能是
0、1、2; - 前两位之后剩余9位数字。
1.2 编码设计原则
表单校验核心准则:永远不信任用户输入内容,不能使用模糊匹配。正则通过逐字符匹配+首尾边界锚定实现精准限制,从语法层面拦截不合规数据。
1.3 正则拆解与落地代码
js
// ^ 起始锚点,1固定首位,[3-9]限制第二位,\d{9}后9位数字,$末尾锚点
const phoneReg = /^1[3-9]\d{9}$/;
// 多组测试用例
const phone1 = '13899887766'; // 合规号码
const phone2 = '12899887766'; // 第二位非法
const phone3 = '1389988776'; // 长度不足
const phone4 = '138998877661';// 长度超标
console.log(phoneReg.test(phone1)); // true
console.log(phoneReg.test(phone2)); // false
console.log(phoneReg.test(phone3)); // false
console.log(phoneReg.test(phone4)); // false
二、正则表达式基础语法
2.1 正则基础概念
JS中正则采用/规则/修饰符字面量写法,匹配逻辑:从左至右逐个字符比对字符串,匹配成功即命中规则。
| 符号 | 作用说明 | 使用示例 |
|---|---|---|
\d |
匹配单个数字0~9 | \d{9}代表连续9个数字 |
[] |
限定单个字符可选范围 | [3-9]匹配3至9任意数字 |
{n} |
精准匹配n次前面字符 | \d{5}连续5位数字 |
^ |
匹配字符串开头 | ^1必须以数字1起始 |
$ |
匹配字符串结尾 | \d{9}$末尾为9个数字 |
\w |
匹配字母、数字、下划线 | \w单个英文/数字/_ |
+ |
匹配1次或多次字符 | \d+一串连续数字 |
2.2 两个核心实例方法
- test():校验匹配,返回布尔值
多用于表单合规性判断,只要存在匹配片段就返回true。
js
const reg = /\d+/;
console.log(reg.test('abc123')); // true
- exec():捕获匹配内容,返回数组/null
可捕获分组内容,无匹配项返回null,适合提取指定字段。
js
const reg = /a(\d)/;
console.log(reg.exec('a6')); // ["a6", "6"]
2.3 g全局修饰符
默认正则匹配到第一个符合条件的内容就停止检索,添加修饰符g(global)开启全局匹配,遍历整串所有匹配内容,提取多组数据必备。
三、JS基础:两大数据类型体系
3.1 基本数据类型(值类型)
包含:Number、String、Boolean、undefined、null,数据保存在栈内存,赋值为值复制,变量之间互不干扰。
3.2 引用数据类型(引用类型)
根类型为Object,数组Array、正则RegExp都是Object派生类型,变量存储堆内存地址。
类型判断易错点:
typeof无法细分引用类型,正则、数组使用typeof结果全是object;精准判定用原型方法:
js
const reg = /\d{6}/;
console.log(typeof reg); // object
console.log(Object.prototype.toString.call(reg)); // [object RegExp]
四、正则搭配字符串三大实战场景
4.1 场景1:提取文本中全部数字
借助String.match()(返回的是数组) + 全局g,快速取出所有连续数字:
js
const str = '价格是100元,进价是80,赚了20元';
const reg = /\d+/g;
const numList = str.match(reg);
console.log(numList); // ['100','80','20']
4.2 场景2:短横线命名转为驼峰命名
核心知识点:()分组捕获、replace回调替换,括号只捕获字符不占用匹配位。
js
// hello-world-hello → helloWorldHello
const str = 'hello-world-hello';
// -(\w):匹配横杠+单个字符,括号单独捕获字母
const reg = /-(\w)/g;
const result = str.replace(reg,(_, char)=>{
return char.toUpperCase();
})
console.log(result);
4.3 场景3:递归实现简易模板渲染
实现{``{字段名}}模板语法替换,循环递归完成全部占位符替换:
js
const template = `我是{{name}},年龄{{age}},性别{{sex}}`;
const person = {
name:'张三',
age:18,
sex:'男'
};
/**
* 模板渲染函数
* @param {String} tpl 原始模板
* @param {Object} data 数据源
* @returns {String} 替换完成字符串
*/
function render(tpl, data){// tp1是字符串,data是person对象
// 捕获{{变量名}}内部字段
const reg = /\{\{(\w+)\}\}/;
// 判断仍存在待替换占位符
if(reg.test(tpl)){
const name = reg.exec(tpl)[1];// 在第一次递归是得到person的name字段
tpl = tpl.replace(reg, data[name]);
// 递归继续替换剩余占位符
return render(tpl, data);
}
return tpl;
}
console.log(render(template, person));
五、全文总结&知识点复盘&避坑指南
全文总结
- 手机号校验关键依靠首尾锚点
^$,缺失边界符号会出现超长字符串误判通过的问题; - 正则核心由边界符、范围符、次数符、分组符组成,
g修饰符实现全局批量匹配; - JS数据类型分为基本值类型、引用类型,
Object.prototype.toString.call()是精准判断引用子类型的标准方案; - 字符串常用API:
match批量提取内容、replace自定义替换逻辑,多占位替换场景优先使用递归。
核心知识点复盘
- 手机号标准正则:
/^1[3-9]\d{9}$/; test做布尔校验,exec捕获分组数据,g开启全局检索;()分组作用:捕获指定片段,不参与字符消耗;replace支持回调函数,动态自定义替换规则;- 多个模板占位符必须递归,单次replace仅能替换一处内容。
常见问题&避坑指南
- ❌ 正则遗漏
^$:手机号校验时1381234567899这类超长字符串会校验成功; - ❌ 提取数字不加
g:match只能拿到第一个数字,剩余数字丢失; - ❌ 使用typeof判断正则/数组:统一返回object,类型识别模糊;
- ❌ 模板替换不使用递归:只替换第一个
{``{xxx}},剩余占位原样保留; - ❌ 手机号第二位范围写成
[0-9]:无法拦截0、1、2开头的非法号段。