1048 数字加密 (20 分)

题目描述:

本题要求实现一种数字加密方法。首先固定一个加密用正整数 A,对任一正整数 B,将其每 1 位数字与 A 的对应位置上的数字进行以下运算:对奇数位,对应位的数字相加后对 13 取余——这里用 J 代表 10、Q 代表 11、K 代表 12;对偶数位,用 B 的数字减去 A 的数字,若结果为负数,则再加 10。这里令个位为第 1 位。

输入格式:
输入在一行中依次给出 A 和 B,均为不超过 100 位的正整数,其间以空格分隔。

输出格式:
在一行中输出加密后的结果。

输入样例:
1234567 368782971
输出样例:
3695Q8118


解题思路:
Alice: 这道题看起来挺普通的啊,怎么通过率这么低呢 ?
Bob: 人不可貌相啊,简洁不代表简单啊。ψ(*`ー´)ψ
Alice: 你觉得有哪些地方会有陷阱呢?
Bob: A B 位数不相等的时候,还有AB的输入会不会是13进制,还有100位的整数用C/C++的整型是存不下的。
Alice: 输入应该不会是13进制的,我们可以试一试。程序按照10进制去写( A = [int(x) for x in A[::-1]]),如果没有RE(run time error,运行时错误)就是10进制的。
Bob: 我们用Python写,不用担心整型变量会溢出的问题。而且我倾向于直接用字符串来存,然后直接把各个位拆开。
Alice: 恩,没有运行时错误,有两个WA(wrong answer, 答案错误)。有两个测试样例没过啊。
Bob: A B 位数不等的时候你怎么写的?
Alice: 对B加密,看案例如果A的长度小于B的长度的话,B多出来的高位可以直接不处理,接上去就好了。如果A的长度大于B的长度,直接按B的每位来就好了啊。
Bob: 我也是这样想的。既然是对B加密,A多出来的部分应该是没用的。真的WA了吗?给我看看代码。
Alice: (^ o^)/~,我想到一种简化的写法,A的长度小于B的长度的时候可以在A的前面加上一些零。如果A的对应位上是零,B对应位上的加密结果就是其自身。这和样例是相符的。
Bob: 会不会B的长度小于A的长度的时候也要在B的前面补上零啊?
Alice: 啊(キ`゚Д゚´)!!这么神奇嘛 (#゚д゚メ)
Bob: 没办法,好像没有别的选项了。虽然看起来不合常理,试一试吧。
Alice: 嘿,还真是这样,这题目。啧啧啧,辣鸡。
Bob: <(▰˘◡˘▰)


代码:

def main():
    A, B = (x for x in input().split())
    # 接收输入的两个字符串,A B。我们可以直接按照字符串来处理,其实这样反而更快一些。
    A = [int(x) for x in A[::-1]]
    # A 是一个整数列表,记录了A 从个位到最高位的每个数字。如 521 -> [1, 2, 5]
    B = [int(x) for x in B[::-1]]
    # 同上
    #如果A, B的长度不同就 把在它们前面补零,让它们的长度相等。
    if len(A) < len(B):
        A.extend([0] * (len(B) - len(A)))
    elif len(A) > len(B):
        B.extend([0] * (len(A) - len(B)))
    answer = []
    for x, _ in enumerate(B):
        # 对于B中的每一位数字,加密。
        if (x + 1) % 2 == 0:
            temp = B[x] - A[x]
            if temp < 0:
                temp += 10
        else:
            temp = (B[x] + A[x]) % 13
            if temp == 10:
                temp = 'J'
            elif temp == 11:
                temp = 'Q'
            elif temp == 12:
                temp = 'K'
        answer.append(temp)
    answer.reverse()
    # 我们从个位开始加密,但是要从最高位开始输出,所以需要翻转加密后的字符串。
    print(''.join([str(x) for x in answer]))
    # 拼接好答案,然后输出。


if __name__ == '__main__':
    main()


易错点:

  • 如果A 和 B的长度相等,按照题意处理即可。如果A的长度小于B的长度,按照样例我们可以在A的前面补上适当的零。这背后的逻辑是,如果A相应的位上是零,加密操作不会改变B对应位上的数字。 那么,疑问来了,如果A的长度大于B呢? 答案竟然(艹皿艹)是在B的前面也补上足够的零。加密操作改变了输入字符串的长度,恩,就是这样。

总结:

  • 我认为通过一些“毛病”来强行给题目增加难度的做法不可取。
  • 但是这样糟糕的题目就是存在,所以不要和一道题死磕。当然,和任何对象死磕都不好。

我想开了

  • 3
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 3
    评论
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值