关于身份证号码...

时间:2021-11-19 20:39:05
请问如何将15位的身份证号码转换为18位的身份证号码??有什么好办法,请给出实例!太感谢啦!!

8 个解决方案

#1


在后面加“000”不行吗?

#2


原作者姓名 otn

介绍
介绍18位身份证号码最后一位校验码的计算方法

读者评分 13 评分次数 3 

正文

介绍18位身份证号码最后一位校验码的计算方法

公民身份号码是特征组合码,由十七位数字本体码和一位校验码组成。排列顺序从左至右依次为:六位数字地址码,八位数字出生日期码,三位数字顺序码和一位数字校验码。

校验方法:
(1)十七位数字本体码加权求和公式
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

(2)计算模
Y = mod(S, 11)

(3)通过模得到对应的校验码
     Y: 0 1 2 3 4 5 6 7 8 9 10
校验码: 1 0 X 9 8 7 6 5 4 3 2


下面是C程序代码:
//        char szSrc1[]="11010519491231002X";
//        DoVerify(szSrc1);
//        char szSrc2[]="440524188001010014";
//        DoVerify(szSrc2);

char DoVerify(const char* pszSrc)
{
    int iS = 0;
    int iW[]={7, 9, 10, 5, 8, 4, 2, 1, 6, 3, 7, 9, 10, 5, 8, 4, 2};
    static char szVerCode[]="10X98765432";
    int i;
    for(i=0;i<17;i++)
    {
        iS += (int)(pszSrc[i]-'0') * iW[i];
    }
    int iY = iS%11;
//    printf("%d %% 11 = iY = %d\n",iS, iY);
//    printf("%c \n",szVerCode[iY]);
    return szVerCode[iY];

}

正文完

#3


http://www.yesky.com/SoftChannel/72357795139158016/20030617/1708250.shtml

#4


15位转18位的规则好像不是这么简单吧。

#5


我处理身份证编号问题的办法是:根据相应规则,使用T-Sql函数。具体如下,保证好用。
CREATE FUNCTION GetIDNumber(@oldNumber varchar(15))
RETURNS varchar(18)
AS
BEGIN
   --保存产生新的身份证编码
   DECLARE @newNumber varchar(18)
   --循环控制变量
   declare @i int
   --合计变量
   declare @sum int
   --Wi:表示第i位置上的加权因子
   --Wi: 7  9 10  5  8  4  2  1  6 3 7 9 10 5 8 4 2 1
   declare @arr_Wi varchar(36)  
   --校正码 
   declare @arr_JYM varchar(22)

   select @arr_Wi='070910050804020106030709100508040201'
   select @arr_JYM='10X98765432'

   --修改老身份证编码,添加 19 ,变成17位编码。
   --如110105491231002  -〉11010519491231002
   select @newNumber = substring(@oldNumber,1,6)+'19'+substring(@oldNumber,7,9)

   select @i=2
   select @sum=0
   while(@i<=18)
   begin
       select @sum = @sum+convert(int,substring(@newNumber,len(@newNumber)-@i+2,1))*convert(int,substring(@arr_Wi,len(@arr_Wi)-@i*2+1,2))
       select @i=@i+1
   end
   select @newNumber = @newNumber + substring(@arr_JYM,(@sum%11)+1,1)

    --********算法说明***************
    --(1)十七位数字本体码加权求和公式
    --S = Ai * Wi, i = 2, ... , 18
    --Y = mod(S, 11)
    --i: 表示号码字符从右至左包括校验码字符在内的位置序号
    --Ai:表示第i位置上的身份证号码字符值
    --Wi:表示第i位置上的加权因子
    --i: 18 17 16 15 14 13 12 11 10 9 8 7  6 5 4 3 2 1
    --Wi: 7  9 10  5  8  4  2  1  6 3 7 9 10 5 8 4 2 1
    --(2)校验码字符值的计算
    --Y:      0 1 2 3 4 5 6 7 8 9 10
    --校验码: 1 0 X 9 8 7 6 5 4 3  2
   RETURN(@newNumber)
END

调用方法是:select 数据库.dbo.getidnumber('111111111111111')

#6


http://yousoft.hi.com.cn/forum_view.asp?forum_id=3&view_id=881

#7


http://www.abkk.com/cn/idcard/
到这个网站去看看吧,会有惊喜的,呵呵!

#8


18位的身份证号码是在原15位身份证号码的第六位和第七位间 加入了“19”两位数字,目的是解决“千年虫”问题。然后再根据这样产生的17位数生成一个校验数加在最后,这里只介绍该校样数的产生算法:
   //使用SPARKS语言,定义%为取余运算符//
 procedure idNoProof()
   integer i,num;
   char proof;
   integer idcode(1:17);
   num=0
   for i=17 to 1 by -1 do 
      num=num+( 2^i % 11 ) * (idcode(18-i));
   repeat
   num=num %11
   case num
      :0 : proof='1'
      :1 : proof='0'
      :2 : proof='X'
      :else : proof=(char)(12-num)
 end idNoProof   
  能不能口算或者用简单笔算出来这个校样数呢?答案是肯定的,程序中多次利用了除以11的余数,而商是没有用的,所以针对人的算法是这样的(只有产生num的值部分): 
num=0 ,j=1//从现在开始要记住num的值//
  for i=1 to 17 do //从最后一位开始算,能简单不少//
     j=(2*j) mod 11 
  //j 的值是2的i次方除以11的余数,当然运算时前面还有句“if 2*j>11 then”//
     num=(j*idcode(18-i) mod 11 + num)mod 11
  repeat   
  运算中只需要记着每次变化后的j和num的当前值就可以了,运算的次数理论上最坏的情况下会求除以11的余数51次,千万不要犯错哈,:)


#1


在后面加“000”不行吗?

#2


原作者姓名 otn

介绍
介绍18位身份证号码最后一位校验码的计算方法

读者评分 13 评分次数 3 

正文

介绍18位身份证号码最后一位校验码的计算方法

公民身份号码是特征组合码,由十七位数字本体码和一位校验码组成。排列顺序从左至右依次为:六位数字地址码,八位数字出生日期码,三位数字顺序码和一位数字校验码。

校验方法:
(1)十七位数字本体码加权求和公式
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

(2)计算模
Y = mod(S, 11)

(3)通过模得到对应的校验码
     Y: 0 1 2 3 4 5 6 7 8 9 10
校验码: 1 0 X 9 8 7 6 5 4 3 2


下面是C程序代码:
//        char szSrc1[]="11010519491231002X";
//        DoVerify(szSrc1);
//        char szSrc2[]="440524188001010014";
//        DoVerify(szSrc2);

char DoVerify(const char* pszSrc)
{
    int iS = 0;
    int iW[]={7, 9, 10, 5, 8, 4, 2, 1, 6, 3, 7, 9, 10, 5, 8, 4, 2};
    static char szVerCode[]="10X98765432";
    int i;
    for(i=0;i<17;i++)
    {
        iS += (int)(pszSrc[i]-'0') * iW[i];
    }
    int iY = iS%11;
//    printf("%d %% 11 = iY = %d\n",iS, iY);
//    printf("%c \n",szVerCode[iY]);
    return szVerCode[iY];

}

正文完

#3


http://www.yesky.com/SoftChannel/72357795139158016/20030617/1708250.shtml

#4


15位转18位的规则好像不是这么简单吧。

#5


我处理身份证编号问题的办法是:根据相应规则,使用T-Sql函数。具体如下,保证好用。
CREATE FUNCTION GetIDNumber(@oldNumber varchar(15))
RETURNS varchar(18)
AS
BEGIN
   --保存产生新的身份证编码
   DECLARE @newNumber varchar(18)
   --循环控制变量
   declare @i int
   --合计变量
   declare @sum int
   --Wi:表示第i位置上的加权因子
   --Wi: 7  9 10  5  8  4  2  1  6 3 7 9 10 5 8 4 2 1
   declare @arr_Wi varchar(36)  
   --校正码 
   declare @arr_JYM varchar(22)

   select @arr_Wi='070910050804020106030709100508040201'
   select @arr_JYM='10X98765432'

   --修改老身份证编码,添加 19 ,变成17位编码。
   --如110105491231002  -〉11010519491231002
   select @newNumber = substring(@oldNumber,1,6)+'19'+substring(@oldNumber,7,9)

   select @i=2
   select @sum=0
   while(@i<=18)
   begin
       select @sum = @sum+convert(int,substring(@newNumber,len(@newNumber)-@i+2,1))*convert(int,substring(@arr_Wi,len(@arr_Wi)-@i*2+1,2))
       select @i=@i+1
   end
   select @newNumber = @newNumber + substring(@arr_JYM,(@sum%11)+1,1)

    --********算法说明***************
    --(1)十七位数字本体码加权求和公式
    --S = Ai * Wi, i = 2, ... , 18
    --Y = mod(S, 11)
    --i: 表示号码字符从右至左包括校验码字符在内的位置序号
    --Ai:表示第i位置上的身份证号码字符值
    --Wi:表示第i位置上的加权因子
    --i: 18 17 16 15 14 13 12 11 10 9 8 7  6 5 4 3 2 1
    --Wi: 7  9 10  5  8  4  2  1  6 3 7 9 10 5 8 4 2 1
    --(2)校验码字符值的计算
    --Y:      0 1 2 3 4 5 6 7 8 9 10
    --校验码: 1 0 X 9 8 7 6 5 4 3  2
   RETURN(@newNumber)
END

调用方法是:select 数据库.dbo.getidnumber('111111111111111')

#6


http://yousoft.hi.com.cn/forum_view.asp?forum_id=3&view_id=881

#7


http://www.abkk.com/cn/idcard/
到这个网站去看看吧,会有惊喜的,呵呵!

#8


18位的身份证号码是在原15位身份证号码的第六位和第七位间 加入了“19”两位数字,目的是解决“千年虫”问题。然后再根据这样产生的17位数生成一个校验数加在最后,这里只介绍该校样数的产生算法:
   //使用SPARKS语言,定义%为取余运算符//
 procedure idNoProof()
   integer i,num;
   char proof;
   integer idcode(1:17);
   num=0
   for i=17 to 1 by -1 do 
      num=num+( 2^i % 11 ) * (idcode(18-i));
   repeat
   num=num %11
   case num
      :0 : proof='1'
      :1 : proof='0'
      :2 : proof='X'
      :else : proof=(char)(12-num)
 end idNoProof   
  能不能口算或者用简单笔算出来这个校样数呢?答案是肯定的,程序中多次利用了除以11的余数,而商是没有用的,所以针对人的算法是这样的(只有产生num的值部分): 
num=0 ,j=1//从现在开始要记住num的值//
  for i=1 to 17 do //从最后一位开始算,能简单不少//
     j=(2*j) mod 11 
  //j 的值是2的i次方除以11的余数,当然运算时前面还有句“if 2*j>11 then”//
     num=(j*idcode(18-i) mod 11 + num)mod 11
  repeat   
  运算中只需要记着每次变化后的j和num的当前值就可以了,运算的次数理论上最坏的情况下会求除以11的余数51次,千万不要犯错哈,:)