Question:
一个信用卡号必须是13到16位的整数。它的开头必须是:
4 Visa卡
5 Master卡
37 American Express卡
6 Discover卡
1954年,IBM的Hans Luhn提出一种算法,用于验证信用卡卡号的有效性。这个算法在确定输入的卡号是否正确,或者这张信用卡是否被扫描仪正确扫描方面是非常有用的。
遵循这个合法性检测可以生成所有的信用卡号,通常称之为Luhn检测或者Mod 10检测,可以如下描述(为了方便解释,假设卡号4388576018402626:
从右到左对偶数位数字翻倍。如果对某个数字翻倍之后的结果是一个两位数,那么就将这两位加在一起得到一位数。
现在将第一步得到的所有一位数相加。
将卡号里从右到左奇数位上的所有数字相加。
将第二步和第三步得到的结果相加。
如果第四步得到的结果能被10整除,那么卡号是合法的;否则,卡号是不合法的。
例如,号码4388576018402626是不合法的,但是号码4388576018410707是合法的。
解决方法1:
#include <iostream>
#include <string>
using namespace std;
int main() {
string card_num;
cout << "请输入信用卡卡号: ";
cin >> card_num;
int len = card_num.size();
int sum = 0;
bool is_double = false;
for(int i=len-1; i>=0; i--) {
int digit = card_num[i] - '0';
// 使偶数位数字翻倍
if(is_double) {
digit *= 2;
if(digit > 9) {
digit -= 9; // 如果结果是两位数,就将两个数字相加得到一位数
}
}
sum += digit;
is_double = !is_double; // 切换到下一个数字的位数
}
// 如果结果能被10整除,说明卡号是合法的
if(sum % 10 == 0) {
cout << "该卡号是合法的。" << endl;
} else {
cout << "该卡号是不合法的。" << endl;
}
return 0;
}
解决方法2:
#include<iostream>
#include<string>
using namespace std;
void main()
{
string s;
cin>>s;
int res=0;
for(int i=0;i<s.length();i++)
{
if(i%2==0)
{
res+=(s[i]-48)*2>=10?(s[i]-48)*2/10+(s[i]-48)*2%10:(s[i]-48)*2;
}
else
{
res+=s[i]-48;
}
}
if(res%10==0&&(s[0]=='4'||s[0]=='5'||s[0]=='3'&&s[1]=='7'||s[0]=='6')&&s.length()<=16&&s.length()>=13)
{
cout<<"卡号合法"<<endl;
}
else
{
cout<<"卡号不合法"<<endl;
}
}