正则是一个应用很广泛的方法,在学校的课程中和刷题过程中都遇到过有关正则表达式的问题,但是一直都没有认真的学习,一般就是用的时候看一眼用完就跑了,今天看到了手写获取url参数的题,借这个机会系统的学习的正则
问题
给你一个get请求的url链接,获取到其中指定的参数
格式:"https://www.baidu.com/t.html?name=mick&age=20"
URL参数是追加到 URL 上的一个名称/值对。参数以问号 (?) 开始并采用 name=value 的格式。如果存在多个 URL 参数,则参数之间用一个 (&) 符隔开。
看到这个题我想到的第一想法就是正则,但是让我们学习一下其他的几种写法
现代方式
直接利用浏览器提供的API,最简单的方式
function getQueryString(name) {
const url_string = "https://www.baidu.com/t.html?name=mick&age=20"; // window.location.href
const url = new URL(url_string);
return url.searchParams.get(name);
}
console.log(getQueryString('name')) // mick
console.log(getQueryString('age')) // 20
利用URL()将字符串转化为URL,然后使用searchParams.get()函数将其中需要的参数提取
老式字符串循环法
核心私信是通过String.split()函数将url不断分割成块,最后获取到自己需要的部分,值得注意的是,url可能是经过编码之后才进行传输的,Url编码的原则就是使用安全的字符(没有特殊用途或者特殊意义的可打印字符)去表示那些不安全的字符。经过编码之后,可以防止歧义(如变量中带有特殊字符导致解析的错误)并允许特殊语言符合(中文)转化为ascii码后传输。所以在处理url之前首先要使用decodeURIComponent进行解码
function getQueryString(name) {
var url_string = "https%3A%2F%2Fwww.baidu.com%2Ft.html%3Fname%3Dmick%26age%3D20"; // window.location.href
url_string=decodeURIComponent(url_string)
var params = url_string.split('?')[1]; // 获取?号后面的参数 name=mick&age=20
if (!params) return null; // 如果无参,返回null
var vars = params.split("&"); // 将参数分割成数组 ['name=mick', 'age=20']
var query_string = {};
for (var i = 0; i < vars.length; i++) {
var pair = vars[i].split("="); // 将参数的key和值进行分割成 ['name', 'mick']
var key = pair[0]; // 参数key
var value = pair[1]; // 参数值
if (name === key) { // 如果匹配到对应key返回
return value;
}
}
return null;
}
console.log(getQueryString('name')) // mick
console.log(getQueryString('age')) // 20
正则式表达法
regular expression(regex,re),使用单个字符串来描述、匹配一系列符合某个句法规则的字符串搜索模式。
在js中,有专门用于进行正则表达的对象RegExp
var patt=new RegExp(pattern,modifiers);
或者更简单的方式:
var patt=/pattern/modifiers;
pattern是具体的匹配模式,而modifiers为修饰符
i | 执行对大小写不敏感的匹配。 |
---|---|
g | 执行全局匹配(查找所有匹配而非在找到第一个匹配后停止)。 |
m | 执行多行匹配。 |
方括号用于查找某个范围内的字符:
[abc] | 查找方括号之间的任何字符。 | ||
---|---|---|---|
[1(https://www.runoob.com/jsref/jsref-regexp-charset-not.html) | 查找任何不在方括号之间的字符。 | ||
[0-9] | 查找任何从 0 至 9 的数字。 | ||
[a-z] | 查找任何从小写 a 到小写 z 的字符。 | ||
[A-Z] | 查找任何从大写 A 到大写 Z 的字符。 | ||
[A-z] | 查找任何从大写 A 到小写 z 的字符。 | ||
[adgk] | 查找给定集合内的任何字符。 | ||
2 | 查找给定集合外的任何字符。 | ||
(red\ | blue\ | green) | 查找任何指定的选项。 |
元字符(Metacharacter)是拥有特殊含义的字符:
元字符 | 描述 |
---|---|
. | 查找单个字符,除了换行和行结束符。 |
w | 查找数字、字母及下划线。 |
W | 查找非单词字符。 |
d | 查找数字。 |
D | 查找非数字字符。 |
s | 查找空白字符。 |
S | 查找非空白字符。 |
b | 匹配单词边界。 |
B | 匹配非单词边界。 |
0 | 查找 NULL 字符。 |
n | 查找换行符。 |
f | 查找换页符。 |
r | 查找回车符。 |
t | 查找制表符。 |
v | 查找垂直制表符。 |
xxx | 查找以八进制数 xxx 规定的字符。 |
xdd | 查找以十六进制数 dd 规定的字符。 |
uxxxx | 查找以十六进制数 xxxx 规定的 Unicode 字符。 |
量词 | 描述 |
---|---|
n+ | 匹配任何包含至少一个 n 的字符串。例如,/a+/ 匹配 "candy" 中的 "a","caaaaaaandy" 中所有的 "a"。 |
n* | 匹配任何包含零个或多个 n 的字符串。例如,/bo*/ 匹配 "A ghost booooed" 中的 "boooo","A bird warbled" 中的 "b",但是不匹配 "A goat grunted"。 |
n? | 匹配任何包含零个或一个 n 的字符串。例如,/e?le?/ 匹配 "angel" 中的 "el","angle" 中的 "le"。 |
n{X} | 匹配包含 X 个 n 的序列的字符串。例如,/a{2}/ 不匹配 "candy," 中的 "a",但是匹配 "caandy," 中的两个 "a",且匹配 "caaandy." 中的前两个 "a"。 |
n{X,} | X 是一个正整数。前面的模式 n 连续出现至少 X 次时匹配。例如,/a{2,}/ 不匹配 "candy" 中的 "a",但是匹配 "caandy" 和 "caaaaaaandy." 中所有的 "a"。 |
n{X,Y} | X 和 Y 为正整数。前面的模式 n 连续出现至少 X 次,至多 Y 次时匹配。例如,/a{1,3}/ 不匹配 "cndy",匹配 "candy," 中的 "a","caandy," 中的两个 "a",匹配 "caaaaaaandy" 中的前面三个 "a"。注意,当匹配 "caaaaaaandy" 时,即使原始字符串拥有更多的 "a",匹配项也是 "aaa"。 |
n$ | 匹配任何结尾为 n 的字符串。 |
3(https://www.runoob.com/jsref/jsref-regexp-ncaret.html) | 匹配任何开头为 n 的字符串。 |
?=n | 匹配任何其后紧接指定字符串 n 的字符串。 |
?!n | 匹配任何其后没有紧接指定字符串 n 的字符串。 |
RegExp 对象方法
方法 | 描述 |
---|---|
compile | 在 1.5 版本中已废弃。 编译正则表达式。 |
exec | 检索字符串中指定的值。返回找到的值,并确定其位置。 |
test | 检索字符串中指定的值。返回 true 或 false。 |
toString | 返回正则表达式的字符串。 |
支持正则表达式的 String 对象的方法
方法 | 描述 | FF | IE |
---|---|---|---|
search | 检索与正则表达式相匹配的值。 | 1 | 4 |
match | 找到一个或多个正则表达式的匹配。 | 1 | 4 |
replace | 替换与正则表达式匹配的子串。 | 1 | 4 |
split | 把字符串分割为字符串数组。 | 1 | 4 |
正则表达式解法
function getQueryString(name) {
var query_string = "?name=mick&age=20"; // window.location.search
if (!query_string) return null; // 如果无参,返回null
var re = /[?&]?([^=]+)=([^&]*)/g;
var tokens;
while (tokens = re.exec(query_string)) {
if (decodeURIComponent(tokens[1]) === name) {
return decodeURIComponent(tokens[2]);
}
}
return null;
}
console.log(getQueryString('name')) // mick
console.log(getQueryString('age')) // 20
正则表达式的用法还有一道题是lc上的表示数组的字符串,当时做的时候十分痛苦就直接看答案了,今天正好补充一下
题目地址:https://leetcode-cn.com/problems/biao-shi-shu-zhi-de-zi-fu-chuan-lcof/
题目描述
数值(按顺序)可以分成以下几个部分:
若干空格
一个 小数 或者 整数
(可选)一个 'e' 或 'E' ,后面跟着一个 整数
若干空格
小数(按顺序)可以分成以下几个部分:
(可选)一个符号字符('+' 或 '-')
下述格式之一:
至少一位数字,后面跟着一个点 '.'
至少一位数字,后面跟着一个点 '.' ,后面再跟着至少一位数字
一个点 '.' ,后面跟着至少一位数字
整数(按顺序)可以分成以下几个部分:
(可选)一个符号字符('+' 或 '-')
至少一位数字
var isNumber = function (s) {
return /^([+-]?((\d*\.\d+)|\d+|(\d+\.\d*)))([eE][+-]?\d+)?$/.test(s.trim())
//行的开始,符号, 浮点数|整数|浮点数 e 符号 整数 匹配行尾 去掉前后空格
};
没有评论