Fe-interview: [js] 第20天 写一个验证身份证号的方法

Created on 5 May 2019  ·  9Comments  ·  Source: haizlin/fe-interview

第20天 写一个验证身份证号的方法

js

Most helpful comment

分析:身份证号码的组成:地址码6位+年份码4位+月份码2位+日期码2位+顺序码3位+校验码1位

function check(val){
    var reg=/^[1-9]\d{5}(19|20)\d{2}((0[1-9])|(1[0-2]))(([0-2][1-9])|(10|20|30|31))\d{3}[0-9Xx]$/;
     return reg.test(val);
}

```
检测省份码
function checkProvice(val)
{
var patten=/^[1-9][0-9]/;
if(patten.test(val))
{
var prov={11:"北京",12:"天津",13:"河北",14:"山西",15:"内蒙古",21:"辽宁",22:"吉林",23:"黑龙江",31:"上海",32:"江苏",33:"浙江",34:"安徽",35:"福建",36:"江西",37:"山东",41:"河南",42:"湖北",43:"湖南",44:"广东",45:"广西",46:"海南",51:"四川",52:"贵州",53:"云南",54:"西藏",50:"重庆",61:"陕西",62:"甘肃",63:"青海",64:"宁夏",65:"新疆",81:"香港",82:"澳门",83:"台湾"};
if(prov[val])
{
return true;
};
}

return false;
}

检测出生日期
function checkBirthDay(val)
{
var patten=/^(19|20)\d{2}((0[1-9])|1[0-2])(([0-2][1-9])|(10|20|30|31))/;
if(patten.test(val))
{
var year=val.substring(0,4);
var month=val.substring(4,6);
var day=val.substring(6,8);

    var date=new Date(year+"-"+month+"-"+day);
    if(date&&date.getMonth()==(parseInt(month)-1))
    {
        return true;
    }

}
return false;

}

检测校验码
function checkVerifyCode(val)
{
var patten=/^[1-9]\d{5}(19|20)\d{2}((0[1-9])|(1[0-2]))(([0-2][1-9])|(10|20|30|31))\d{3}[0-9X]$/;
var ratio=[7,9,10,5,8,4,2,1,6,3,7,9,10,5,8,4,2];
var codeArr=[1,0,"X",9,8,7,6,5,4,3,2];
var code=val.substring(17);
if(patten.test(val))
{
var sum=0;
for(var i=0;i<17;i++)
{
sum+=val[i]*ratio[i];
}
console.log(sum)
var remainder=sum%11;
if(codeArr[remainder]==code)
{
return true;
}
}
return false;
}

function checkIndetityCardNo(val){
var province=val.substring(0,2);
if(checkProvice(province))
{
var date=val.substring(6,14);
if(checkBirthDay(date))
{
return checkVerifyCode(val);
}
}
return false;
}

All 9 comments

分析:身份证号码的组成:地址码6位+年份码4位+月份码2位+日期码2位+顺序码3位+校验码1位

function check(val){
    var reg=/^[1-9]\d{5}(19|20)\d{2}((0[1-9])|(1[0-2]))(([0-2][1-9])|(10|20|30|31))\d{3}[0-9Xx]$/;
     return reg.test(val);
}

```
检测省份码
function checkProvice(val)
{
var patten=/^[1-9][0-9]/;
if(patten.test(val))
{
var prov={11:"北京",12:"天津",13:"河北",14:"山西",15:"内蒙古",21:"辽宁",22:"吉林",23:"黑龙江",31:"上海",32:"江苏",33:"浙江",34:"安徽",35:"福建",36:"江西",37:"山东",41:"河南",42:"湖北",43:"湖南",44:"广东",45:"广西",46:"海南",51:"四川",52:"贵州",53:"云南",54:"西藏",50:"重庆",61:"陕西",62:"甘肃",63:"青海",64:"宁夏",65:"新疆",81:"香港",82:"澳门",83:"台湾"};
if(prov[val])
{
return true;
};
}

return false;
}

检测出生日期
function checkBirthDay(val)
{
var patten=/^(19|20)\d{2}((0[1-9])|1[0-2])(([0-2][1-9])|(10|20|30|31))/;
if(patten.test(val))
{
var year=val.substring(0,4);
var month=val.substring(4,6);
var day=val.substring(6,8);

    var date=new Date(year+"-"+month+"-"+day);
    if(date&&date.getMonth()==(parseInt(month)-1))
    {
        return true;
    }

}
return false;

}

检测校验码
function checkVerifyCode(val)
{
var patten=/^[1-9]\d{5}(19|20)\d{2}((0[1-9])|(1[0-2]))(([0-2][1-9])|(10|20|30|31))\d{3}[0-9X]$/;
var ratio=[7,9,10,5,8,4,2,1,6,3,7,9,10,5,8,4,2];
var codeArr=[1,0,"X",9,8,7,6,5,4,3,2];
var code=val.substring(17);
if(patten.test(val))
{
var sum=0;
for(var i=0;i<17;i++)
{
sum+=val[i]*ratio[i];
}
console.log(sum)
var remainder=sum%11;
if(codeArr[remainder]==code)
{
return true;
}
}
return false;
}

function checkIndetityCardNo(val){
var province=val.substring(0,2);
if(checkProvice(province))
{
var date=val.substring(6,14);
if(checkBirthDay(date))
{
return checkVerifyCode(val);
}
}
return false;
}

不是很清楚 身份证号码的规则 写不出来正则

  1. 粗暴型: 只考虑位数、最后的 x \d{17}[\dXx]
  2. 一般型:
  3. 前 6 位区号 \d{6}
  4. 中间年份 \d{4} 可以增加年份判断
  5. 月份 01-12 月 0[1-9]|1[0-2]
  6. 日期 01-31 日 0[1-9]|[12][0-9]|3[01]
  7. 顺序码 \d{3}
  8. 校验码 [\dXx] 其实有校验算法,可以根据算法再做一次检查 https://zhuanlan.zhihu.com/p/21286417
const isValidIdentity = (id) => {
  if (
    /^\d{6}\d{4}(0[1-9]|1[0-2])(0[1-9]|[12][0-9]|3[01])\d{3}[\dXx]$/.test(id)
  ) {
    return true;
  } else {
    return false;
  }
};

console.log(isValidIdentity(123456789012345678));
console.log(isValidIdentity(123456190011301234));
console.log(isValidIdentity("123456190013301234"));
console.log(isValidIdentity("123456190010321234"));
console.log(isValidIdentity('12345619001130123x'));
console.log(isValidIdentity('12345619001130123X'));
const isValidID = (id)=> {
   var id_reg = /^\d{6}(1[8-9]|2[0-9])\d{2}(0[1-9]|1[0-2])([012][0-9]|3[01])\d{3}[\dXx]$/
   return id_reg.test(id)? true:false
}

这个不清楚规则

不太清楚规则
var reg=/^[1-9]\d{5}(19|20)\d{2}((0[1-9])|(1[0-2]))(([0-2][1-9])|(10|20|30|31))\d{3}[0-9Xx]$/;
reg.test(val);
还是贴个上面的答案把

function fn(x) {
            return /^\d{6}\d{4}(0[1-9]|1[0-2])(0[1-9]|[12][0-9]|3[01])\d{3}[\dXx]$/.test(x) ? true : false;
        }

粗暴型: 只考虑位数、最后的 x \d{17}[\dXx]
一般型:
前 6 位区号 \d{6}
中间年份 \d{4} 可以增加年份判断
月份 01-12 月 0[1-9]|1[0-2]
日期 01-31 日 0[1-9]|[12][0-9]|3[01]
顺序码 \d{3}
校验码 [\dXx] 其实有校验算法,可以根据算法再做一次检查 https://zhuanlan.zhihu.com/p/21286417
const isValidIdentity = (id) => {
if (
/^\d{6}\d{4}(0[1-9]|1[0-2])(0[1-9]|[12][0-9]|3[01])\d{3}[\dXx]$/.test(id)
) {
return true;
} else {
return false;
}
};

console.log(isValidIdentity(123456789012345678));
console.log(isValidIdentity(123456190011301234));
console.log(isValidIdentity("123456190013301234"));
console.log(isValidIdentity("123456190010321234"));
console.log(isValidIdentity('12345619001130123x'));
console.log(isValidIdentity('12345619001130123X'));

还有15位的身份证。。。

Was this page helpful?
0 / 5 - 0 ratings