本文有参考qs库的源码
要求:
let str = 'http://www.xxx.com/?lx=0&from=weixin&n=100#video';
console.log(str.queryURLParams()); //=>{lx:0,from:'weixin',n:100,HASH:'video'}
console.log(str.queryURLParams('lx')); //=>0
console.log(str.queryURLParams('HASH')); //=>video
问号传参的作用:
- 客户端页面跳转的时候,基于问号传递参数实现数据的传输
- 客户端向服务器端发送请求,GET系列请求都是基于问号参数实现的数据传递的
- 前端路由中,组件和组件之间的通信也可以基于问号传参
- ...
问号传递参数的格式: urlencoded
数据被编码成以 '&' 分隔的键-值对, 同时以 '=' 分隔键和值。
具体查看MDN content type application/x-www-form-urlencoded
queryURLParams 是项目中一个非常常用的获取问号参数的方法。
三种方法手写实现:
字符串截取处理
String.prototype.queryURLParams = function queryURLParams(attr) {
let self = this,
obj = {};
let askIndex = self.indexOf('?'),
wellIndex = self.indexOf('#'),
askText = '',
wellText = '';
askIndex === -1 ? askIndex = self.length : null;
wellIndex === -1 ? wellIndex = self.length : null;
if (askIndex < wellIndex) {//判断?和#哪个在前面
//'http://www.xxx.com/#video?lx=0&from=weixin&n=100'
askText = self.substring(askIndex + 1, wellIndex);
wellText = self.substring(wellIndex + 1);
} else {
askText = self.substring(askIndex + 1);
wellText = self.substring(wellIndex + 1, askIndex);
}
// 井号获取信息了
if (wellText) obj['HASH'] = wellText;
// 问号获取信息了
if (askText) {
askText.split('&').forEach(item => {
let [key, value] = item.split('=');//解构赋值
obj[key] = value;
});
}
return typeof attr === "undefined" ? obj : (obj[attr] || '');
};
利用A元素对象的相关属性(OOP)
a DOM对象中的属性: hash/host/hostname/pathname/protocol/search ... 基于这些私有属性即可获取到URL中每一部分的信息
String.prototype.queryURLParams = function queryURLParams(attr) {
let self = this,
obj = {};
let link = document.createElement('a');
link.href = self;
let {
search,
hash
} = link;
link = null;//手动释放内存
if (hash) obj['HASH'] = hash.substring(1);
if (search) {
search.substring(1).split('&').forEach(item => {
let [key, value] = item.split('=');
obj[key] = value;
});
}
return typeof attr === "undefined" ? obj : (obj[attr] || '');
};
直接正则处理
正则 /[^?&=#]/ 意义:等号两边不能是这几个符号,因为这几个符号是有特殊含义的
String.prototype.queryURLParams = function queryURLParams(attr) {
let self = this,
obj = {};
let reg1 = /([^?&=#]+)=([^?&=#]+)/g,
reg2 = /#([^?&=#]+)/g;
self.replace(reg1, (_, key, value) => obj[key] = value);
self.replace(reg2, (_, hash) => obj['HASH'] = hash);
return typeof attr === "undefined" ? obj : (obj[attr] || '');
};
self.replace(reg1, (_, key, value) => obj[key] = value);
回调函数中,每一次匹配到就会执行一次,第一个参数是正则匹配到的完整的字符串,第二个参数是分组1,第三个参数是分组2
URLSearchParams
URLSearchParams 接口定义了一些实用的方法来处理 URL 的查询字符串。
ie浏览器不支持,其他浏览器可以直接使用