并不是随便的信用卡号都是合法的,它必须通过Luhn算法来验证。
验证过程:
1. 从卡号最后一位数字开始,逆向将奇数位(1、3、5等等)相加。
2. 从卡号最后一位数字开始,逆向将偶数位数字,先乘以2(如果乘积为两位数,则将其减去9),再求和。
3. 将奇数位总和加上偶数位总和,结果应该可以被10整除。
例1
卡号是:5432 1234 5678 8881
则奇数(用红色标出)
奇数位和结果:
- 1+8+8+4+6+4+2+2+4=35
偶数位乘以2(如果乘积为两位数,则将其减去9)的结果:
- 8*2=16-9=7
- 8*2=16-9=7
- 7*2=14-9=5
- 5*2=10-9=1
- 3*2=6
- 1*22=2
- 3*2=6
- 5*2=10-9=1
- 7+7+5+1+6+2+6+1=35。
最后35+35=70 可以被10整除,认定校验通过。
例2
4417 1234 5678 9112
第二个信用卡提供者展示的卡图片上的号码为4417 1234 5678 9112.
MII是4 (银行和金融业),发行者标识符为441712 (VISA合作伙伴),帐号为345678911,校验位是2.
我们来应用一下Luhn算法检验4417 1234 5678 9112,跟上一个例子一样。 4 4 1 7 1 2 3 4 5 6 7 8 9 1 1 2
4x2=8 4 1x2=2 7 1x2=2 2 3x2=6 4 5x2=10 6 7x2=14 8 9x2=18 1 1x2=2 2
8 4 2 7 2 2 6 4 10-9=1 6 14-9=5 8 18-9=9 1 2 2
8 4 2 7 2 2 6 4 1 6 5 8 9 1 2 2
将最后一行的数字相加得到的结果为69不是10的倍数,结论是4417 1234 5678 9112不是有效的信用卡号码。
如果将校验为由2变成3,卡号变为4417 1234 5678 9113, 这个号码可以通过Luhn算法的检验,因为所有数字相加的结果为70可以10整除。所以表面上来看4417 1234 5678 9113是一个合法的卡号。
注意:
1. 对于偶数个数字的卡号(4417 1234 5678 9112)。将所有第奇数个数字乘以2,如果大于9就减去9。将所有得到的偶数于原先的偶数全部相加其结果必须是10的倍数,否则卡号无效。
2. 如果卡号(456 3510 1008 9033 5387)有奇数个数字,则应将第偶数个数字乘以2,其余步骤相同。
3. 特性:不管号码的长度是奇数还是偶数。都是从倒数第二个数字开始,每隔一位乘以2,如果大于9就减去9。
php实现如下
- $num = ‘5432123456788881’;
- function is_valid_credit_card($num){
- $num = strrev($num); // 这样可以解决卡号是奇数还是偶数的问题
- for ($i=1,$j=strlen($num); $i<=$j; $i++) {
- if (($i%2)==0) {
- $val = $num[$i]*2;
- if ($val>9)
- $val-=9;
- } else {
- $val = $num[$i];
- }
- $sum +=$val;
- }
- return (($sum%10)==0); // 返回true则号码有效。
- }