导言
在我们的日常开发中,很容易碰到需要实名验证的场景,因此本文主要记录一下18位身份证号码的校验。
身份证规则说明
第二代身份证的编码规则如下:
户口登记地行政区划代码(6位) + 出生年月日(8位) + 顺序码(3位) + 校验码(1位)
详细说明:
户口登记地行政区划代码:(注意:可能有些地区的行政区划代码会有所变更,所以这份资料也不一定完整。)详细见行政区划代码
出生年月日:没有什么需要注意的
顺序码:奇数为男性 偶数为女性
校验码: 用于身份证号码的校验(详情见下方)。
校验码算法
身份证校验方法:将本体码各位数字乘以对应的加权因子并求和,除以11得到余数,根据余数通过校验码对照表查得校验码。
加权因子:
加权因子.png
校验码:
校验码.png
算法例子:
本体码为11010519491231002
第一步: 各位数与对应加权因子乘积求和17+19+010+15+***=167
第二步:对求和进行除11得余数167%11=2
第三步:根据余数2对照校验码得X
因此完整身份证号为:11010519491231002X
js代码示例(包含长度、出生年月、性别、校验码校验等4重校验。)
function checkCardId(cardId){
// 0 、校验长度
if(cardId.length !== 18){
return {
code : 404,
message : '身份证号码错误,请检查!'
}
}
// 1 、号码规则校验(未验证,如果要用到此部分代码请自行验证。)
// var format = /^(([1][1-5])|([2][1-3])|([3][1-7])|([4][1-6])|([5][0-4])|([6][1-5])|([7][1])|([8][1-2]))\d{4}(([1][9]\d{2})|([2]\d{3}))(([0][1-9])|([1][0-2]))(([0][1-9])|([1-2][0-9])|([3][0-1]))\d{3}[0-9xX]$/;
// if (!format.test(cardId)) {
// return {
// code : 404,
// message : '校验不通过'
// };
// }
// 2、出生年月校验(固定位置)
let year = cardId.substr(6,4);
let month = cardId.substr(10,2);
let day = cardId.substr(12,2);
let birthday = `${year}-${month}-${day}`;
if(!checkBirthday(birthday)){
console.log(birthday);
return {
code : 404,
message : '校验失败'
}
}
// 3、 性别校验(需要的就打开注释)
// let sexCode = cardId.substr(14,3);
// if(sexCode % 2 === 1){
// console.log('男性');
// }else{
// console.log('女性');
// }
// 4、校验码校验
// 提取最后一位校验码
let code = cardId.substr(17, 1);
// 提取需要校验的字符串(前17位)
let checkStr = cardId.substr(0,17);
let sum = 0;
// 加权因子
let ruleArr = [7,9,10,5,8,4,2,1,6,3,7,9,10,5,8,4,2];
// 使用加权因子计算所得结果对应的校验码(模11,有10种结果)
let checkCodeArr = [1,0,'x',9,8,7,6,5,4,3,2];
checkStr.split('').map(function(item,index){
sum += Number(item)*ruleArr[index];
})
let checkNum = sum % 11;
let caculateCode = checkCodeArr[checkNum];
if(checkNum === 2){
code = code.toLowerCase();
}else{
code = Number(code);
}
if(caculateCode === code){
return {
code : 200,
message : '校验通过'
}
}else{
return {
code : 404,
message : '校验不通过'
}
}
}
function checkBirthday(birthday){
var r = /^(?:(?!0000)[0-9]{4}-(?:(?:0[1-9]|1[0-2])-(?:0[1-9]|1[0-9]|2[0-8])|(?:0[13-9]|1[0-2])-(?:29|30)|(?:0[13578]|1[02])-31)|(?:[0-9]{2}(?:0[48]|[2468][048]|[13579][26])|(?:0[48]|[2468][048]|[13579][26])00)-02-29)$/;
if(!r.test(birthday)){
return false;
}else{
return true;
}
}
附注
通过此校验并不代表身份证是有效的!!!
网友评论