`

C#实现的18位身份证格式验证算法[详细版]

阅读更多

项目分析

<shapetype id="_x0000_t75" stroked="f" filled="f" path="m@4@5l@4@11@9@11@9@5xe" o:preferrelative="t" o:spt="75" coordsize="21600,21600"><stroke joinstyle="miter"></stroke><formulas><f eqn="if lineDrawn pixelLineWidth 0"></f><f eqn="sum @0 1 0"></f><f eqn="sum 0 0 @1"></f><f eqn="prod @2 1 2"></f><f eqn="prod @3 21600 pixelWidth"></f><f eqn="prod @3 21600 pixelHeight"></f><f eqn="sum @0 0 1"></f><f eqn="prod @6 1 2"></f><f eqn="prod @7 21600 pixelWidth"></f><f eqn="sum @8 21600 0"></f><f eqn="prod @7 21600 pixelHeight"></f><f eqn="sum @10 21600 0"></f></formulas><path o:connecttype="rect" gradientshapeok="t" o:extrusionok="f"></path><lock aspectratio="t" v:ext="edit"></lock></shapetype><shape id="_x0000_i1026" style="WIDTH: 335.25pt; HEIGHT: 378pt" type="#_x0000_t75"><imagedata o:title="正面" src="file:///C:%5CDOCUME~1%5CADMINI~1%5CLOCALS~1%5CTemp%5Cmsohtml1%5C01%5Cclip_image001.jpg"></imagedata></shape>

<shape id="_x0000_i1027" style="WIDTH: 213pt; HEIGHT: 29.25pt" type="#_x0000_t75"><imagedata o:title="组件" src="file:///C:%5CDOCUME~1%5CADMINI~1%5CLOCALS~1%5CTemp%5Cmsohtml1%5C01%5Cclip_image003.jpg"></imagedata></shape>

第一部分生成号码

代码概述

1.事件:void frmAlgorithm_Load(object sender, EventArgs e)

描述:首先,在窗体加载时,调用"void GetDiscInfo(string sFilenName)"读取"DiscInfo.txt"中的信息,然后在"cbProvince"中显示读取的信息(使用了外设组件"bsProvince")

2.事件: void cbProvince_SelectedIndexChanged(object sender, EventArgs e)

描述:在选择省份时,调用"List<clsAdministrativeDivisionsCode> GetSomeCodes(string sCondition)""cbCities"中显示省份的下属市或县(使用了外设组件"bsCity")

----------------核心代码-↓↓↓------------------------------------

3.事件: void btnGenID_Click(object sender, EventArgs e)

描述: 方法1:"List<string> GetID()" //生成14位数号码,并返回18位数号码

方法2: "List<string> GenRnd(int iSex)" //返回3位数的顺序码

方法3: "string GenParityBit(string s17)" //返回1位数的校验码

根据选择好的生日和性别生成号码.首先调用方法1.在方法1中调用了方法2和方法3,方法2返回3位数的顺序码,方法3返回1位数的校验码.方法1自身生成14位数号码+3位顺序码+1位校验码=18位号码,返回给外设组件"bsID",然后显示.

----------------核心代码-↑↑↑---------------------------------------

源代码

class clsAdministrativeDivisionsCode

{

private string adCode;

private string adName;

public clsAdministrativeDivisionsCode(string code, string name)

{ adCode = code; adName = name; }

public string AdCode

{

get { return adCode; }

set { adCode = value; }

}

public string AdName

{

get { return adName; }

set { adName = value; }

}

}// class clsAdministrativeDivisionsCode

public class frmAlgorithm : Form

{

private int maxNum = 500;

List<clsAdministrativeDivisionsCode> provinceCode = new List<clsAdministrativeDivisionsCode>();

List<clsAdministrativeDivisionsCode> cityCode = new List<clsAdministrativeDivisionsCode>();

List<string> ID = new List<string>();

private void frmAlgorithm_Load(object sender, EventArgs e)

{

GetDiscInfo("DiscInfo.txt");

bsProvince.DataSource = provinceCode;

cbProvince.DataSource = bsProvince;

cbProvince.DisplayMember = "AdName";

cbProvince.ValueMember = "AdCode";

cbProvince.SelectedIndex = -1; //引发cbProvince_SelectedIndexChanged事件

lblMsg.Text = @"请在文本框中输入位有效身份证号,验证通过后方可解读。";

}//void frmAlgorithm_Load

private void GetDiscInfo(string sFilenName)

{

using (StreamReader sr = new StreamReader(Environment.CurrentDirectory + @"\" + sFilenName, Encoding.Default)) {

string sLine = string.Empty;

Regex re = new Regex(@"[\s]{1,}", RegexOptions.Compiled); //指定至少匹配个空白字符,程序集

while (!sr.EndOfStream) { //如果流不在末尾,则循环

sLine = sr.ReadLine();

sLine = re.Replace(sLine, " ");

string[] sTemp = sLine.Split(new char[] { ' ' });

if (sTemp[0].EndsWith("0000")) {

provinceCode.Add(new clsAdministrativeDivisionsCode(sTemp[0],sTemp[1])); }

else {

if (sTemp[0].EndsWith("00"))

cityCode.Add(new clsAdministrativeDivisionsCode(sTemp[0],sTemp[1]));

else

if (sTemp[1].EndsWith("市辖区"))

cityCode.Add(new clsAdministrativeDivisionsCode(sTemp[0], " " + sTemp[1]));

else

cityCode.Add(new clsAdministrativeDivisionsCode(sTemp[0], " " + sTemp[1]));

}//else

}//while

}//using

}//void GetDiscInfo(string sFilenName)

//事件将在省份列表的选择中被引发

private void cbProvince_SelectedIndexChanged(object sender, EventArgs e)

{

List<clsAdministrativeDivisionsCode> tempCity = new List<clsAdministrativeDivisionsCode>();

if (cbProvince.SelectedValue != null)

{

//调用Substring(0, 2)的目的是:提取公共部分来查找下属市或县

//例如:山西省的省号为140000,则其下属市或县的号码都以14开头

//140101 市辖区 140105 小店区

//140106 迎泽区 140122 阳曲县

tempCity = GetSomeCodes(cbProvince.SelectedValue.ToString().Substring(0, 2));

if (tempCity != null)

{

bsCity.DataSource = tempCity;

cbCities.DataSource = bsCity;

cbCities.DisplayMember = "AdName";

cbCities.ValueMember = "AdCode";//显示信息

}//if

}//if

}//cbProvince_SelectedIndexChanged

private List<clsAdministrativeDivisionsCode> GetSomeCodes(string sCondition)

{

List<clsAdministrativeDivisionsCode> tempCity = new List<clsAdministrativeDivisionsCode>();

foreach (clsAdministrativeDivisionsCode temp in cityCode)

if (sCondition == temp.AdCode.Substring(0, 2))//比较省份号码的公共部分

tempCity.Add(temp);

return tempCity;//返回下属市或县 }//List<clsAdministrativeDivisionsCode> GetSomeCodes(string sCondition)

----------------核心代码-↓↓↓------------------------------------

private void btnGenID_Click(object sender, EventArgs e)

{

//省略一些检查代码

this.Cursor = Cursors.WaitCursor;//把光标设置成沙漏状

bsID.DataSource = GetID(); //获取外设组件bsID的数据源(GetID()获得)

lbID.DataSource = bsID; //显示个身份证号

this.Cursor = Cursors.Default;//还原光标

}//void btnGenID_Click

private List<string> GetID()

{

List<string> tempID = new List<string>();

List<string> sexRndNum = GenRnd(rbMan.Checked?0:1);//单选框''被选中,值为0;否则为1

string str18 = string.Empty;

for (int i = 0; i < maxNum; i++)

{

string str17=string.Empty;

string sCity = cbCities.SelectedValue.ToString();//获取下属市或县的号码,共6

string sYMD=dtpBirth.Value.Year.ToString() +

dtpBirth.Value.Month.ToString().PadLeft(2, '0') +

tpBirth.Value.Day.ToString().PadLeft(2, '0');//获取年月日,共8

str17=sCity+sYMD+sexRndNum[i];//17位的身份证号,还需最后一位校验码

str18 = str17 + GenParityBit(str17);//18位的身份证号

tempID.Add(str18);

}

return tempID;

}//List<string> GetID()

private List<string> GenRnd(int iSex)

{

Random rd = new Random();//随机数对象

List<string> sTemp = new List<string>();

int i = 0;

while (i < maxNum)//maxNum=500;

{

int rndNum = rd.Next(0, 1000); //0<=rndNum<=999

if (rndNum % 2 == iSex) rndNum++;

if (rndNum >= 1000) continue; //if (rndNum == 1000)

string s3 = rndNum.ToString().PadLeft(3, '0');

//右对齐字符串,不满位的,在左边添加'0'填充例:002,054,586

if (!sTemp.Contains(s3))//确保没有重复的号码

{

sTemp.Add(s3);

i++;

}

}//while

return sTemp;

}// List<string> GenRnd(int iSex)

//不知道下面这些数据从哪来是正常的,是根据公式来算的

private string GenParityBit(string s17)

{

int[] Weight = new int[] { 7, 9, 10, 5, 8, 4, 2, 1, 6, 3, 7, 9, 10, 5, 8, 4, 2 };

string Parity = "10X98765432";

int s = 0;

for (int i = 0; i < s17.Length; i++)

{

s += Int32.Parse(s17[i].ToString()) * Weight[i];

}

return Parity[s % 11].ToString();//返回校验码

}//string GenParityBit(string s17)

----------------核心代码-↑↑↑---------------------------------------

} //public class frmAlgorithm

验证解读部分

<shape id="_x0000_i1025" style="WIDTH: 273pt; HEIGHT: 306.75pt" type="#_x0000_t75"><imagedata o:title="背面" src="file:///C:%5CDOCUME~1%5CADMINI~1%5CLOCALS~1%5CTemp%5Cmsohtml1%5C01%5Cclip_image004.jpg"></imagedata></shape>

代码概述

1. 事件: void btnVerification_Click(object sender, EventArgs e)

描述:首先获取输入的身份证号码,然后把它拆分成4,分别是

1) 行政地区码(6),使用"bool isDiscValid(string s)"来验证.

2) 出生日期(7-14),使用" bool isBirthValid(string s)"来验证.

3) 顺序码(15-17),使用"bool isSexValid(string s)"来验证.

4) 校验码(18),使用" bool isParityValid(string s18)"来验证.

源代码

class clsAdministrativeDivisionsCode

{

private void btnVerification_Click(object sender, EventArgs e)

{

//省略提示……

Regex reg = new Regex(@"^\d{17}(\d|X)");//匹配18位数字,最后一位可以是数字或X

string sTemp = tbVerification.Text;

lbCardInfo.Items.Clear();

if (sTemp == string.Empty) { return; }

if (sTemp.Length != 18) { return; }

if (reg.Matches(sTemp).Count == 0) { return; }

if (!isDiscValid(sTemp.Substring(0, 6))) { return; }//验证行政地区码

if (!isBirthValid(sTemp.Substring(6, 8))) { return; }//验证生日

else

lbCardInfo.Items.Add(string.Format("出生日期:{0}{1}{2}", sTemp.Substring(6, 4), sTemp.Substring(10, 2), sTemp.Substring(12, 2)));

if (!isSexValid(sTemp.Substring(14, 3))) { return; }//验证性别

else { lbCardInfo.Items.Add("性别:" + ((Convert.ToInt32(sTemp.Substring(14, 3)) % 2 == 0) ? "" : "")); }

if (!isParityValid(sTemp)) { return; }//验证最后一位校验码

lbCardInfo.Items.Insert(0, "身份证号:" + sTemp);

lbCardInfo.Items.Insert(0, "验证解读信息:");

lbCardInfo.Items.Add("完成验证!");

}//void btnVerification_Click

private bool isDiscValid(string s)

{

bool iFlag = false;

foreach (clsAdministrativeDivisionsCode cadc in cityCode)

{

if (cadc.AdCode == s)

{

string st = s.Substring(0, 2);

foreach (clsAdministrativeDivisionsCode capc in provinceCode)

{

if (capc.AdCode.Substring(0, 2) == st)

{

lbCardInfo.Items.Add("省或直辖市名称:" + capc.AdName);

break;

}

}//foreach

foreach (clsAdministrativeDivisionsCode caac in cityCode)

{

if (caac.AdCode == s.Substring(0, 4) + "00")

{

lbCardInfo.Items.Add("市名称:" + caac.AdName.TrimStart());

break;

}

分享到:
评论

相关推荐

    C#实现的18位身份证格式验证算法

    C#实现的18位身份证格式验证算法.txt

    C#实现的18位身份证格式验证算法.doc

    C#实现的18位身份证格式验证算法.doc

    C#身份证验证算法归类.pdf

    C#身份证验证算法归类.pdf

    C# 源码 判断 身份证号 有效性

    C# 源码 判断 身份证号 有效性 包含:长度 校验位 出生日期 省份 等判断算法

    身份证号码验证示例源码2008-4-22

    身份证号码验证示例源码 &lt;br&gt;中国身份证号码验证,支持15,18位,可验证成功90%的身份证号 利用正则进行身份证算法验证 &lt;br&gt;非常不错

    C#开发实例大全(基础卷).软件开发技术联盟(带详细书签) PDF 下载

    实例142 身份证号从15位升到18位的算法 186 实例143 歌德巴赫猜想的算法实现 187 实例144 八皇后问题的算法实现 188 实例145 百钱百鸡的算法实现 190 实例146 韩信点兵的算法实现 191 实例147 实现斐波纳契数列求和 ...

    C#经验技巧宝典1-5

    0083 身份证从15位升至18位算法 60 0084 十进制数转二进制数的算法 60 0085 十进制数转八进制数的算法 61 0086 十进制数转十六进制数的算法 62 0087 二、八、十六进制数转十进制数的算法 63 3.4 ...

    C#编程经验技巧宝典

    58 &lt;br&gt;0081 文本中首字母改为大写 59 &lt;br&gt;0082 C#随机数的产生 59 &lt;br&gt;0083 身份证从15位升至18位算法 60 &lt;br&gt;0084 十进制数转二进制数的算法 60 &lt;br&gt;0085 十进制数转八进制数的算法 61...

    C#程序开发范例宝典(第2版).part08

    实例229 C#中实现文件拖放 317 实例230 文件比较 318 实例231 获取文件夹中的图标资源 319 实例232 获取文件夹下的所有文件夹及文件的名称 321 第7章 操作系统与Windows相关程序 324 7.1 启动相关 325 实例...

    C#程序开发范例宝典(第2版).part12

    实例229 C#中实现文件拖放 317 实例230 文件比较 318 实例231 获取文件夹中的图标资源 319 实例232 获取文件夹下的所有文件夹及文件的名称 321 第7章 操作系统与Windows相关程序 324 7.1 启动相关 325 实例...

    C#程序开发范例宝典(第2版).part02

    实例229 C#中实现文件拖放 317 实例230 文件比较 318 实例231 获取文件夹中的图标资源 319 实例232 获取文件夹下的所有文件夹及文件的名称 321 第7章 操作系统与Windows相关程序 324 7.1 启动相关 325 实例...

    C#.net_经典编程例子400个

    273 实例190 获取窗口文本 273 实例191 判断文件是否正在被使用 274 实例192 在程序中调用.HLP文件 275 实例193 C#中实现文件拖放 276 实例194 文件比较 276 第7章 操作系统与Windows...

    C#开发中常用的加密解密方法汇总

    相信很多人在开发过程中经常会遇到需要对一些重要的信息进行加密处理,今天给大家分享我个人总结的一些加密算法: 常见的加密方式分为可逆和不可逆两种方式  可逆:RSA,AES,DES等  不可逆:常见的MD5,SHAD等 一、...

    C#程序开发范例宝典(第2版).part13

    实例229 C#中实现文件拖放 317 实例230 文件比较 318 实例231 获取文件夹中的图标资源 319 实例232 获取文件夹下的所有文件夹及文件的名称 321 第7章 操作系统与Windows相关程序 324 7.1 启动相关 325 实例...

Global site tag (gtag.js) - Google Analytics