'Turkish Identity Number Verification

How can I make sure that the given text is Turkish Identity Number? I have seen js version here and phthon version here

Also, posted a question couple of days ago for swift version here.

Turkish Identity Verification is not checks only if its numeric, it has some other functions too. Let me be more clear, It is numeric and has 11 digits. For example Let assume that first 9 digits are represented by d, and the last ones represented by c:

Identity Number = d1 d2 d3 d4 d5 d6 d7 d8 d9 c1 c2

10th digit must be,

c1 = ( (d1 + d3 + d5 + d7 + d9) * 7 - (d2 + d4 + d6 + d8) ) mod10

11th must be,

c2 = ( d1 + d2 + d3 + d4 + d5 + d6 + d7 + d8 + d9 + c1 ) mod10

and it never starts with "0". For example, "87836910956" is a Turkish Identity Number.

Now I have to use this validation in android/java.



Solution 1:[1]

You could shorten it a little bit without losing readability to:

private static boolean verifyNumber(String nationalityNumberStr) {
    if(nationalityNumberStr.startsWith("0") || !nationalityNumberStr.matches("[0-9]{11}") ){
        return false;
    }

    int [] temp = new int [11];
    for (int i = 0; i < 11; i++){
        temp[i] = Character.getNumericValue(nationalityNumberStr.toCharArray()[i]);
    }

    int c1 = 0;
    int c2 = temp[9];
    for(int j = 0; j < 9; j++){
        if(j%2 == 0) {
           c1 += temp[j] * 7;
        }
        else {
           c1 -=  temp[j];
        }
        c2 += temp[j];
    }

    return  temp[9]== c1 % 10 && temp[10] == c2 %10;
}

Solution 2:[2]

Here is how I ended up:

   private static boolean verifyNumber(String nationalityNumberStr) {
            try {
                String tmp = nationalityNumberStr;

                if(tmp.toCharArray()[0] != '0'){
                    //cannot start with 0
                    if (tmp.length() == 11) {
                        //should be 11 digits
                        int totalOdd = 0;

                        int totalEven = 0;

                        for (int i = 0; i < 9; i++) {
                            int val = Integer.valueOf(tmp.substring(i, i + 1));

                            if (i % 2 == 0) {
                                totalOdd += val;
                            } else {
                                totalEven += val;
                            }
                        }

                        int total = totalOdd + totalEven + Integer.valueOf(tmp.substring(9, 10));

                        int lastDigit = total % 10;

                        if (tmp.substring(10).equals(String.valueOf(lastDigit))) {
                            int check = (totalOdd * 7 - totalEven) % 10;

                            if (tmp.substring(9, 10).equals(String.valueOf(check))) {
                                return true;
                            }
                        }
                    }
                }

            } catch (Exception e) {
                e.printStackTrace();
            }

            return false;

Solution 3:[3]

Thanks for all the answers but they all miss something. Builtin Java modulo operator causes a problem for this validation. Builtin Java module operator produces negative modules for negative numbers which causes validation to fail. Instead of using built-in Java module operator, one needs to use Math.floorMod(x, y) method from Math library. That way modulo of a negative number produces positive number which is what expected in the algorithm.

I will share my implementatation:

/*
Tc No = d1 d2 d3 d4 d5 d6 d7 d8 d9 c1 c2
c1 = ( (d1 + d3 + d5 + d7 + d9) * 7 - (d2 + d4 + d6 + d8) ) mod10
c2 = ( d1 + d2 + d3 + d4 + d5 + d6 + d7 + d8 + d9 + c1 ) mod10
*/
public static boolean isValidIdentityNumber(String identityNumber) {
  int d1 = Character.getNumericValue(identityNumber.charAt(0));
  int d2 = Character.getNumericValue(identityNumber.charAt(1));
  int d3 = Character.getNumericValue(identityNumber.charAt(2));
  int d4 = Character.getNumericValue(identityNumber.charAt(3));
  int d5 = Character.getNumericValue(identityNumber.charAt(4));
  int d6 = Character.getNumericValue(identityNumber.charAt(5));
  int d7 = Character.getNumericValue(identityNumber.charAt(6));
  int d8 = Character.getNumericValue(identityNumber.charAt(7));
  int d9 = Character.getNumericValue(identityNumber.charAt(8));
  int d10 = Character.getNumericValue(identityNumber.charAt(9));
  int d11 = Character.getNumericValue(identityNumber.charAt(10));
  int c1 = Math.floorMod((d1 + d3 + d5 + d7 + d9) * 7 - (d2 + d4 + d6 + d8), 10);
  int c2 = Math.floorMod(d1 + d2 + d3 + d4 + d5 + d6 + d7 + d8 + d9 + c1, 10);
  return c1 == d10 && c2 == d11;

}

Solution 4:[4]

Sorry but the code above ( written by Eritrean) is missing some rules. So it does not work.

  • For the short version working code is below ( C# ):

    public static bool IsValidTcknShortCode(string tckn)
    {
        int internalSum = 0, sumFirst9Digit = 0, sumFirst10Digit = 0, current = 0, tckn10thDigit, tcknLastDigit;
    
        try
        {
            if (tckn.Length != 11 || !tckn.All(char.IsDigit) || tckn.Substring(0, 1) == "0")
                return false;
    
    
            for (int i = 1; i < tckn.Length - 1; i++)
            {
                current = int.Parse(tckn[i - 1].ToString());
    
                if (i % 2 != 0)
                    internalSum += (current * 7);
                else
                    internalSum -= current;
    
                sumFirst9Digit += current;
            }
    
            tckn10thDigit = int.Parse(tckn[9].ToString());
            tcknLastDigit = int.Parse(tckn[10].ToString());
            sumFirst10Digit = sumFirst9Digit + tckn10thDigit;
            return (internalSum % 10 == tckn10thDigit && sumFirst10Digit % 10 == tcknLastDigit);
        }
        catch (Exception ex)
        {
            string exMessage = ex.Message;
            return false;
        }
    }
    
  • For a longer code but which I believe much more readable in terms of validation rules readability is below ( C# );

    public static bool IsValidTckn(string tckn)
    {
        int sum13579 = 0, sum2468 = 0, sumFirst10Digit = 0, current = 0, tckn10thDigit, tcknLastDigit;
    
        try
        {
            // TC Kimlik numaralar? 11 basamaktan olu?maktad?r. 
            if (tckn.Length != 11)
                throw new ArgumentException("Length of TCKN must equal to 11");
    
            // Her hanesi rakamsal de?er içerir.
            if (!tckn.All(char.IsDigit))
                throw new ArgumentException("TCKN must only consists of numeric values");
    
            // ?lk hane 0 olamaz
            if (tckn.Substring(0, 1) == "0")
                throw new ArgumentException("TCKN must not start with 0");
    
    
            for (int i = 1; i < tckn.Length - 1; i++)
            {
                current = int.Parse(tckn[i - 1].ToString());
    
                if (i % 2 == 0)
                    sum2468 += current;
                else
                    sum13579 += current;
            }
    
            tckn10thDigit = int.Parse(tckn[9].ToString());
            sumFirst10Digit = sum13579 + sum2468 + tckn10thDigit;
    
            // 1. 3. 5. 7. ve 9. hanelerin toplam?n?n 7 kat?ndan, 2. 4. 6. ve 8. hanelerin toplam? ç?kart?ld???nda, elde edilen sonucun Mod 10’u bize 10. haneyi verir.
            if (((sum13579 * 7) - sum2468) % 10 != tckn10thDigit)
                throw new ArgumentException("Not Valid TCKN");
    
    
            tcknLastDigit = int.Parse(tckn[10].ToString());
    
            // 1. 2. 3. 4. 5. 6. 7. 8. 9. ve 10. hanelerin toplam?ndan elde edilen sonucun 10’a bölümünden kalan, yani Mod10’u bize 11. haneyi verir.
            if (sumFirst10Digit % 10 != tcknLastDigit)
                throw new ArgumentException("Not Valid TCKN");
        }
        catch (Exception ex)
        {
            string exMessage = ex.Message;
            return false;
        }
    
        return true;
    }
    

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1
Solution 2 rozeri dilar
Solution 3 fiver6
Solution 4