身份证的验证无非就是长度地区码的验证。关键是有一部分的软件没有实现对最后一位校验码的校验。这里主要说这个,也算mark一下。其中最重要的就是最后一位校验位的计算。其过程如图:
他的公式是:
一句话就是前17位与其权重(权重:2的i次幂除以11的余数,i为从1开始的位置序号)乘积的和相对于11的余数。
下边再贴一下JAVA的代码(此代码来源于网络,但是我去除了其他的验证,文末会贴出其地址):
import java.util.Calendar;
import java.util.GregorianCalendar;
import java.util.HashMap;
import java.util.Map;
/**
* 身份证验证的工具(支持5位或18位省份证) 身份证号码结构: 17位数字和1位校验码:6位地址码数字,8位生日数字,3位出生时间顺序号,1位校验码。
* 地址码(前6位):表示对象常住户口所在县(市、镇、区)的行政区划代码,按GB/T2260的规定执行。 出生日期码,(第七位
* 至十四位):表示编码对象出生年、月、日,按GB按GB/T7408的规定执行,年、月、日代码之间不用分隔符。
* 顺序码(第十五位至十七位):表示在同一地址码所标示的区域范围内,对同年、同月、同日出生的人编订的顺序号, 顺序码的奇数分配给男性,偶数分配给女性。
* 校验码(第十八位数): 十七位数字本体码加权求和公式 s = sum(Ai*Wi), i = 0,,16,先对前17位数字的权求和;
* Ai:表示第i位置上的身份证号码数字值.Wi:表示第i位置上的加权因.Wi: 7 9 10 5 8 4 2 1 6 3 7 9 10 5 8 4 2;
* 计算模 Y = mod(S, 11) 通过模得到对应的校验码 Y: 0 1 2 3 4 5 6 7 8 9 10 校验码: 1 0 X 9 8 7 6 5
* 4 3 2
*/
public class IDCardUtil {
final static int[] PARITYBIT = { '1', '0', 'X', '9', '8', '7', '6', '5', '4', '3', '2' };
final static int[] POWER_LIST = { 7, 9, 10, 5, 8, 4, 2, 1, 6, 3, 7, 9, 10, 5, 8, 4, 2 };
/**
*
* 身份证校验位验证
*
*/
public static boolean isIDCard(String certNo) {
if (certNo == null || (certNo.length() != 15 && certNo.length() != 18))
return false;
final char[] cs = certNo.toUpperCase().toCharArray();
// 校验位数
int power = 0;
for (int i = 0; i < cs.length; i++) {
if (i == cs.length - 1 && cs[i] == 'X')
break;// 最后一位可以 是X或x
if (cs[i] < '0' || cs[i] > '9')
return false;
if (i < cs.length - 1) {
power += (cs[i] - '0') * POWER_LIST[i];
}
}
return cs[cs.length - 1] == PARITYBIT[power % 11];
}
public static void main(String[] args) {
boolean mark = isIDCard("你的身份证");
System.out.println(mark);
}
}
)
最后贴一下所借鉴内容的地址:
代码:https://www.oschina.net/code/snippet_1859292_39120。
图片:http://jingyan.baidu.com/album/7f41ececff944a593d095c8c.html?picindex=5。
这篇博客MARK 的意味很强,希望也可以帮到一些刚接触程序的新人。