0

如何计算答案以使答案不是硬编码的解决方案?就像我想输入另一个信用卡号一样,我该如何返回该新信用卡的结果?另外,如何创建一个 x 列表,而不是像现在这样将值除以 2 的方式?

另外这里是原始问题供参考:

信用卡号码使用 Luhn 的公式 3 进行验证。实现一个程序,将信用卡号码作为一个多维数组(您可以假设它正好由 16 列组成),并返回一个包含值的列表Valid如果它是有效的卡号,否则无效。

进行有效性测试的一种方法如下:
1. 从最右边的数字,即校验位,向左移动,每隔一个数字加一倍;如果这个加倍运算的乘积大于 9(例如,8 2 = 16),则将乘积的数字相加(例如,16:1 + 6 = 7、18:1 + 8 = 9)。
2. 取所有数字的总和。
3.若总数能被10整除,则根据卢恩公式该数有效;否则无效。

注意:您可以将卡号操作为字符串(使用索引和切片来提取数字等)或整数(使用整数除法和余数来操作数字)。

我的脚本:

    import numpy as py

    x = [[7,1],[6,3],[4,5],[6,2],[7,8],[3,4],[6,8],[3,9]] #credit card numbers
    x2 = np.array(x)
    evryothernum = x2[:,1]       #returns every other number / every seconds digit
    evryothernum2 = np.multiply(evryothernum,2)
    sumdigits = []

    def card_validate(x):
        evryothernum = x2[:,1]        #valid
        evryothernum2 = np.multiply(evryothernum,2) #multiplys         evryothernum by 2
        b=np.sort(evryothernum2, axis = None) #sorts the evryothernum2 array in order
        b2 = np.array(b)
        b3 = b2[4:8] #shows the highest values aka greater than 9 
        b3
        b3 = [1,7,7,9]
        newb3 = np.sum(b3)
        newx2 = np.sum(x2[:,0])
        total = np.sum(newb3+newx2)
        if ( (total % 10) == 0 ):
            print "Valid"
        else:
            print "Invalid"
        return card_validate()

有没有更简单的方法可以在没有 Numpy 的情况下做到这一点?

4

2 回答 2

0

这里有几种方法。第一个是“Luhn 算法”维基百科页面(链接)上的伪代码直接移植到 Python 。第二个使用查找表来处理每隔一个数字的预先计算的加倍值:

def checkLuhn(purportedCC):
     sm = 0
     nDigits = len(purportedCC)
     parity = nDigits % 2
     for i in range(nDigits):
         digit = int(purportedCC[i])
         if i % 2 == parity:
             digit = digit * 2
             if digit > 9:
                 digit = digit - 9
         sm = sm + digit
     return (sm % 10) == 0

def check(s):
    lookup = [0,2,4,6,8,1,3,5,7,9]
    digits = [int(c) for c in reversed(s)] # count odd/even from the right
    odd = digits[::2]
    even = digits[1::2]
    total = sum(odd) + sum(lookup[c] for c in even)
    return total % 10 == 0

cards = '1111222233334444','1111222233334445','01111222233334444'

for card in cards:
    print(card,check(card))
    print(card,checkLuhn(card))

输出(注意如果正确完成,前导零不会影响验证):

1111222233334444 True
1111222233334444 True
1111222233334445 False
1111222233334445 False
01111222233334444 True
01111222233334444 True
于 2017-11-20T01:04:14.467 回答
0

The following can be used to implement the logic without using numpy

a=[[4,0,1,2,8,8,8,8,8,8,8,8,1,8,8,1],[4,0,1,2,8,8,8,8,8,8,8,8,1,8,8,2]] #array of credit card numbers
def validate(creditcard_numbers,tmp):
    even_index=-1

    for j in range(0,16): 
        sum_val=0
        if even_index%2 ==0:  #index calculation for even indices
            val=creditcard_numbers[even_index]*2 
            if val>9:   # add the digits if the value got after multiplying by 2 is two digit number
                while val !=0:
                    rem=val%10
                    val=val/10
                    sum_val=sum_val+rem

                tmp[even_index]=sum_val  #append the temporary list with the new values which is got by adding the digits if the result of multiplying by 2 is a 2 digit number

            else:
                tmp[even_index]=val

        else:
            tmp[even_index]=creditcard_numbers[even_index]
        even_index=even_index-1

    total=0
    for i in tmp:
        total=total+i
    if total%10 == 0:
        return "valid"
    else:
        return "invalid"


for creditcard_numbers in a:
    print creditcard_numbers
    tmp=[0]*len(creditcard_numbers) #temporary list with zeros's 
    result=validate(creditcard_numbers,tmp)
    print result

**OUTPUT : [4, 0, 1, 2, 8, 8, 8, 8, 8, 8, 8, 8, 1, 8, 8, 1]

valid

[4, 0, 1, 2, 8, 8, 8, 8, 8, 8, 8, 8, 1, 8, 8, 2]

invalid **

于 2017-11-19T17:01:52.177 回答