PHP验证德国税务Id(SteuerIdentificationsNummer)

PHP验证德国税务Id(SteuerIdentificationsNummer),php,validation,Php,Validation,德国税务Id()具有以下属性: 它有11个数字 第一位数字不能是0 在前十位中:一个数字正好出现两到三次,一个或两个数字出现零次,其他数字正好出现一次 最后一个数字是校验和 第三个要点对我来说有点难用优雅的方式解决。我已经有了其他三个bulletpoints的代码,但是我很想得到最后一个bulletpoints的输入,因此这可以作为其他人的一个小参考 # validate tax number $taxNumber = $_POST['taxNumber']; e

德国税务Id()具有以下属性:

  • 它有11个数字
  • 第一位数字不能是0
  • 在前十位中:一个数字正好出现两到三次,一个或两个数字出现零次,其他数字正好出现一次
  • 最后一个数字是校验和
  • 第三个要点对我来说有点难用优雅的方式解决。我已经有了其他三个bulletpoints的代码,但是我很想得到最后一个bulletpoints的输入,因此这可以作为其他人的一个小参考

    # validate tax number
            $taxNumber = $_POST['taxNumber'];
            echo preg_replace("/[^0-9]/", "", $taxNumber);
    
            if (strlen($taxNumber != 11)) {
                # 11 digits
                $taxNumberValid = false;
            } else if ($taxNumber[0] == "0") {
                # first digit != 0
                $taxNumberValid = false; 
            } else {
                # one digit two times, one digit zero times
    
    
                # checksum
                $numbers = str_split($taxNumber);
                $sum = 0;
                $product = 10;
                for ($i = 0; $i <= 9; $i++) {
                    $sum = ($numbers[$i] + $product) % 10;
                     if ($sum == 0) {
                         $sum = 10;
                     }
                     $product = ($sum * 2) % 11;
                }
                $checksum = 11 - $product;
                if ($checksum == 10) {
                    $checksum = 0;
                }
    
                if ($taxNumber[10] != $checksum) {
                    $taxNumberValid = false;
                }
            }
    
    #验证税号
    $taxNumber=$_POST['taxNumber'];
    echo preg_替换(“/[^0-9]/”,“,$taxNumber”);
    如果(strlen($taxNumber!=11)){
    #11位数字
    $taxNumberValid=false;
    }else if($taxNumber[0]=“0”){
    #第一位数字!=0
    $taxNumberValid=false;
    }否则{
    #一位数两次,一位数零次
    #校验和
    $numbers=str_split($taxNumber);
    $sum=0;
    $product=10;
    
    对于($i=0;$i),此代码解决了以下问题:

    // remove whitespaces, slashes & other unnecessary characters
    $taxNumber = preg_replace("/[^0-9]/", "", $taxNumber);
    
    // by default the taxnumber is correct
    $taxNumberValid = true;
    
    // taxnumber has to have exactly 11 digits
    if (strlen($taxNumber) != 11) {
        $taxNumberValid = false;                
    }
    
    // first digit cannot be 0
    if ($taxNumber[0] == "0") {
        $taxNumberValid = false; 
    } 
    
    /* 
     make sure that within the first ten digits:
         1.) one digit appears exactly twice or thrice
         2.) one or two digits appear zero times
         3.) and oll other digits appear exactly once once
    */
    $digits = str_split($taxNumber);
    $first10Digits = $digits;
    array_pop($first10Digits);
    $countDigits = array_count_values ($first10Digits);
    if (count($countDigits) != 9 && count($countDigits) != 8) {
        $taxNumberValid = false;
    }
    
    // last check: 11th digit has to be the correct checkums
    // see http://de.wikipedia.org/wiki/Steueridentifikationsnummer#Aufbau_der_Identifikationsnummer
    $sum = 0;
    $product = 10;
    for($i = 0; $i <= 9; $i++) {
        $sum = ($digits[$i] + $product) % 10;
         if ($sum == 0) {
             $sum = 10;
         }
         $product = ($sum * 2) % 11;
    }
    $checksum = 11 - $product;
    if ($checksum == 10) {
        $checksum = 0;
    }
    if ($taxNumber[10] != $checksum) {
        $taxNumberValid = false;
    }
    
    //删除空格、斜杠和其他不必要的字符
    $taxNumber=preg_替换(“/[^0-9]/”,“,$taxNumber);
    //默认情况下,taxnumber是正确的
    $taxNumberValid=true;
    //税号必须正好有11位数字
    如果(strlen($taxNumber)!=11){
    $taxNumberValid=false;
    }
    //第一位数字不能是0
    如果($taxNumber[0]=“0”){
    $taxNumberValid=false;
    } 
    /* 
    确保在前十位数字内:
    1.)一个数字正好出现两到三次
    2.)一个或两个数字出现零次
    3.)和其他数字只出现一次
    */
    $digits=str_split($taxNumber);
    $first10Digits=$digits;
    数组_pop($first10位);
    $countDigits=数组\计数\值($first10位);
    如果(计数($countDigits)!=9和计数($countDigits)!=8){
    $taxNumberValid=false;
    }
    //最后一次检查:第11位数字必须是正确的检查
    //看http://de.wikipedia.org/wiki/Steueridentifikationsnummer#Aufbau_der_Identifikationsnummer
    $sum=0;
    $product=10;
    
    对于($i=0;$i),根据@Pascal Klein的回答,下面是如何在JS中编写它:

    函数计数值(arr){
    返回arr.reduce((对象,项目)=>{
    obj[项目]=obj[项目]?++obj[项目]:1;
    返回obj;
    }, {});
    }
    功能验证素(tin){
    常数tinLength=11;
    //Taxnumber必须正好有11位数字。
    如果(锡长度!==锡长度){
    返回false;
    }
    //第一位数字不能是0。
    如果(tin[0]=“0”){
    返回false;
    }
    /* 
    确保在前十位数字内:
    1.)一个数字正好出现两到三次
    2.)一个或两个数字出现零次
    3.)所有其他数字只显示一次
    */
    const tinArray=tin.split(“”).slice(0,-1);
    const valueCount=countValues(tinArray);
    const valueCountLength=Object.keys(valueCount.length);
    如果(valueCountLength!==8&&valueCountLength!==9){
    返回false;
    }
    //第11位数字必须与checkum匹配。
    设和=0;
    设乘积=10;
    for(设i=0;i
    这里有一个解决方案(在Javascript中)考虑了所有规则

    功能验证(tin){
    //允许空格和斜杠(/)作为数字分隔符
    tin=tin.replace(/| \//g,“”);
    //11位,第一位不允许为0
    如果(!/^[1-9][0-9]{10}$/.测试(tin)){
    返回false;
    }
    常数firstTen=锡片(0,10);
    //计算每个数字出现的次数
    常量出现次数=前十次
    .拆分(“”)
    .reduce((acc,d)=>acc.set(d,(acc.get(d)| | 0)+1),new Map());
    常量键=[…引用.键()];
    常量值=[…引用.值()];
    //如果一个数字出现两次,则键的长度为9
    //如果一个数字出现三次或两个不同的数字出现两次
    //每个长度为8
    如果(keys.length!==9&&keys.length!==8){
    返回false;
    }
    如果(keys.length==8){
    //检查出现次数最多的数字出现的次数
    const maxaccessions=values.reduce((max,num)=>Math.max(max,num));
    //如果maxaccurrencess为2,我们知道两个不同的数字出现了两次
    //每个。这不是有效的tin。
    //最后一个限制是一个数字不能连续出现三次
    如果(maxaccurrencess==2 | |/(\d)\1\1/。测试(前十个)){
    返回false;
    }
    }
    //计算校验和数字
    设m11=10;
    设m10=0;
    for(设i=0;i<10;i++){
    m10=(parseInt(tin[i],10)+m11)%10;
    如果(m10==0){
    m10=10;
    }
    m11=(2*m10)%11;
    }
    设数字=11-m11;
    如果(数字===10){
    数字=0;
    }
    返回数字===parseInt(tin[10],10);
    }
    
    因此礼仪建议您在问题中显示当前的验证代码,如果有人帮助您,则不要将其作为奖品。@feeela请查看您自己的链接,gregexp只验证字符串是否由11位数字组成,中间用两个破折号分隔,因此在这里根本没有帮助。@user574632您是对的,我只是升级了一下用我的代码在帖子中添加所有10位数字,然后使用如何?在此之后,可能只有一个键可用