题目解析第四期来了,通过将一道一道题目的深度刨析,让我们一起培养我们的算法思维吧!
💕💕💕预告,本例题包含对矩阵的螺旋输出操作、逆鞍点的寻找等…

文章目录

  • 一、数字螺旋方阵
  • 二、求矩阵中的逆鞍点
  • 三、旋转矩阵
  • 四、两个矩阵之积
  • 五、古典问题:兔子
  • 六、素数查找
  • 七、水仙花数
  • 八、将一个正整数分解质因数
  • 九、统计
  • 十、求和
  • 一、数字螺旋方阵

    🎈🎈🎈输入一个正整数n,要求输出n×n个数字构成的螺旋方阵。

    输入格式: 首先输入一个正整数T,表示测试数据的组数,然后是T组测试数据。每组测试输入一个正整数n(0~20)。

    输出格式: 对于每组测试,输出n×n的数字螺旋方阵。(各行数据间间隔6个字符宽度。)

    第一步,“首先输入一个正整数T,表示测试数据的组数,然后是T组测试数据。”,我们读懂并且搞定输入:

    T = eval(input())
    for i in range(T):
        n = eval(input())
    

    第二步,“每组测试输入一个正整数n(0~20)”,限制n的数据范围:

     if n>20:
            print("error!")
     else:
    

    第三步,“输入一个正整数n,要求输出n×n个数字构成的螺旋方阵”,例如我们输入的n为2:

    第一列 第二列
    4 3
    2 1
    我们需要完成上述效果。
    第四步,编写逻辑函数实现要求:
    当输入n的值为0或者1的时候输出0和1:
    def spot(tup, x, y, num, n):
        if n <= 0: return 0
        if n == 1:
            tup[x][y] = num
    

    当n属于[2,20),我们需要逐行、逐列地对矩阵进行赋值,不难发现:

    数据从下标为【0,0】的元素开始沿着逆时针减少。
    第一行,向右移动,第一个下标x=0不变,第二个下标y=0增加:

        for i in range(n):
            tup[x][y + i] = num
            num -= 1
    

    最后一列,向下移动,第一个下标x=0增加,第二个坐标y=n-1不变:

        for i in range(n - 1):
            tup[x + 1 + i][y + n - 1] = num
            num -= 1
    

    最后一行,向左移动,第一个下标x=n-1不变,第二个下标y=n-2减少:

        for i in range(n - 1):
            tup[x + n - 1][y + n - 2 - i] = num
            num -= 1
    

    第一列,向上移动,第一个下标x=n-2开始减少,第二个下标y=0不变:

        for i in range(n - 2):
            tup[x + n - 2 - i][y] = num
            num -= 1
    

    第一圈即最外圈已经排完,接下来重复上述操作逐步向内:

      spot(tup, x + 1, y + 1, num, n - 2)
    

    完整代码:

    def spot(tup, x, y, num, n):
        if n <= 0: return 0
        if n == 1:
            tup[x][y] = num
        for i in range(n):
            tup[x][y + i] = num
            num -= 1
        for i in range(n - 1):
            tup[x + 1 + i][y + n - 1] = num
            num -= 1
        for i in range(n - 1):
            tup[x + n - 1][y + n - 2 - i] = num
            num -= 1
        for i in range(n - 2):
            tup[x + n - 2 - i][y] = num
            num -= 1
        spot(tup, x + 1, y + 1, num, n - 2)
    
    
    T = eval(input())
    for i in range(T):
        n = eval(input())
        if n>20:
            print("error!")
        else:
            ls = [[0] * n for i in range(n)]
            spot(ls, 0, 0, n * n, n)
            for x in ls:
                print("%4d" * n % tuple(x))
    
    

    运行效果:

    二、求矩阵中的逆鞍点

    🎈🎈🎈求出n×m二维整数数组中的所有逆鞍点。这里的逆鞍点是指在其所在的行上最大,在其所在的列上最小的元素。若存在逆鞍点,则输出所有逆鞍点的值及其对应的行、列下标。若不存在逆鞍点,则输出“Not”。要求至少使用一个自定义函数。

    输入格式: 测试数据有多组,处理到文件尾。每组测试的第一行输入n和m(都不大于100),第二行开始的n行每行输入m个整数。

    输出格式:
    对于每组测试,若存在逆鞍点,则按行号从小到大、同一行内按列号从小到大的顺序逐行输出每个逆鞍点的值和对应的行、列下标,每两个数据之间一个空格;若不存在逆鞍点,则在一行上输出“Not”(引号不必输出)。

    第一步,分析题目输入输出,发现本题并没有说明以何种符号结束输入,于是我们选择while循环主体模式:

    while True:
        try:
            n, m = map(int, input().split(" "))
            if n>100 or m>100:
                print("error!")
                break
            spot(n,m)
        except:
            break
    

    第二步,题目分析:

    第一列 第二列 第三列 第四列
    1 2 3 4
    5 6 7 8
    9 10 11 12
    13 14 15 16
    在这样一个矩阵中,我们需要输出4和4的坐标0,4。
    第三步,逻辑代码实现;
    def spot(a,b):
        line = {}
        column = {}
        for i in range(1, a + 1):
            tmp = list(map(int, input().split()))
            line[i] = tmp
        tmp = []
        for j in range(1, b + 1):
            tmp = []
            for i in range(1, a + 1):
                tmp.append(line[i][j - 1])
            column[j] = tmp
        num = 0
        for i in range(1, a + 1):
            for j in range(1, b + 1):
                if line[i][j - 1] == max(line[i]) and line[i][j - 1] == min(column[j]):
                    num += 1
                    print("{} {} {}".format(line[i][j - 1], i - 1, j - 1))
        if num == 0:
            print("Not")
    

    完整代码:

    def spot(a,b):
        line = {}
        column = {}
        for i in range(1, a + 1):
            tmp = list(map(int, input().split()))
            line[i] = tmp
        tmp = []
        for j in range(1, b + 1):
            tmp = []
            for i in range(1, a + 1):
                tmp.append(line[i][j - 1])
            column[j] = tmp
        num = 0
        for i in range(1, a + 1):
            for j in range(1, b + 1):
                if line[i][j - 1] == max(line[i]) and line[i][j - 1] == min(column[j]):
                    num += 1
                    print("{} {} {}".format(line[i][j - 1], i - 1, j - 1))
        if num == 0:
            print("Not")
    while True:
        try:
            n, m = map(int, input().split(" "))
            if n>100 or m>100:
                print("error!")
                break
            spot(n,m)
        except:
            break
    

    运行效果:

    三、旋转矩阵

    🎈🎈🎈对于一个奇数n阶方阵,请给出经过顺时针方向m次旋转后的结果。

    输入格式:
    测试数据有多组,处理到文件尾。每组测试的第一行输入2个整数n,m(1<n<20,1≤m≤100),接下来输入n行数据,每行n个整数。

    输出格式: 对于每组测试,输出奇数阶方阵经过m次顺时针方向旋转后的结果。每行中各数据之间留一个空格。

    第一步,同样发现题目没有明确地输入结束标志,选则while结构。
    第二步,输入格式;

    题目中,要求n的值在(1,20)、m的值在[1,100];定义l列表运用map()函数将数插入。

      n, m = map(int, input().split())
            if  1<n<20 and 1<=m<=100:
                l = list()
                for i in range(n):
                    l.append(list(map(int, input().split())))
    

    第三步,核心算法;
    🎈🎈🎈从右边逐步将每一列进行翻转,记得把翻转后的数据储存到一个新的空矩阵中!!!

        for x in range(m):
                    data = []
                    for i in range(n):
                        t = []
                        for j in range(n):
                            t.insert(0, l[j][i])
                        data.append(list(t))
                        t.clear()
                    l = data
                for i in range(n):
                    for j in range(n-1):
                        print(l[i][j], end=" ")
                    print(l[i][n-1])
    

    完整代码:

    while True:
        try:
            n, m = map(int, input().split())
            if  1<n<20 and 1<=m<=100:
                l = list()
                for i in range(n):
                    l.append(list(map(int, input().split())))
                for x in range(m):
                    data = []
                    for i in range(n):
                        t = []
                        for j in range(n):
                            t.insert(0, l[j][i])
                        data.append(list(t))
                        t.clear()
                    l = data
                for i in range(n):
                    for j in range(n-1):
                        print(l[i][j], end=" ")
                    print(l[i][n-1])
            else:
                print("error!")
                break
        except:
            break
    

    运行效果:

    四、两个矩阵之积

    🎈🎈🎈输入整数m、p、n,再输入一个m行p列的整数矩阵A和一个p行n列的整数矩阵B,求两个矩阵的乘积AB

    输入格式: 测试数据有多组,处理到文件尾。每组测试数据的第一行输入n(1<m,p,n<10),接下来分别输入A矩阵和B矩阵。

    输出格式: 对于每组测试,输出m行,每行n个整数,表示AB的结果,每行中每两个数据之间留一个空格。

    第一步,搞定输入格式要求:

     m,p,n=map(int,input().split())
            if 1<m<10 and 1<n<10 and 1<p<10:
    

    第二步,创建两个行、列分别为(m,p)、(p,n)的矩阵,并为其输入值。

    for i in range(m):
                        l.append(list(map(int,input().split())))
          
                for i in range(p):
                        x.append(list(map(int,input().split())))
    

    第三步,核心算法:

     for i in range(m):
                    for u in range(n):
                        sum=0
                        for j in range(p):
                            pro=l[i][j]*x[j][u]
                            sum=sum+pro
    

    完整代码:

    while True:
        try:
            m,p,n=map(int,input().split())
            if 1<m<10 and 1<n<10 and 1<p<10:
                l=[]
                x=[]
                for i in range(m):
                        l.append(list(map(int,input().split())))
          
                for i in range(p):
                        x.append(list(map(int,input().split())))
               
                k=0
    
                res=[[0]*n for i in range(m)]
               
    
    
    
    
                for i in range(m):
                    for u in range(n):
                        sum=0
                        for j in range(p):
                            pro=l[i][j]*x[j][u]
                            sum=sum+pro
                        
                        res[i][u]=sum
            
    
            for x in res:
                print(("%d " * n % tuple(x)).strip())
        except:
            break
    

    运行效果:

    五、古典问题:兔子

    🎈🎈🎈有一对兔子,从出生后第3个月起每个月都生一对兔子,小兔子长到第三个月后每个月又生一对兔子, 假如兔子都不死,问每个月的兔子总数为多少?

    第一个月 第二个月 第三个月 第四个月 第五个月 第六个月
    1对 1对 2对 3对 5对 8对

    答案:

    for i in range(1,22):
        print ('%12ld %12ld' % (f1,f2), end=" ")
        if (i % 3) == 0:
            print ('')
        f1 = f1 + f2
        f2 = f1 + f2
    

    运行效果:

    六、素数查找

    🎈🎈🎈 判断1-100之间有多少个素数,并输出所有素数。

    答案:

    h = 0
    leap = 1
    from math import sqrt
    for m in range(1,101):
        k = int(sqrt(m + 1))
        for i in range(2,k + 1):
            if m % i == 0:
                leap = 0
                break
        if leap == 1:
            print ('%-4d' % m)
            h += 1
            if h % 10 == 0:
                print ('')
        leap = 1
    print ('The number is %d' % h)
    

    运行效果:

    七、水仙花数

    🎈🎈🎈打印出所有的"水仙花数",所谓"水仙花数"是指一个三位数,其各位数字立方和等于该数本身。

    答案:

    for n in range(100,1000):
        i = n / 100
        j = n / 10 % 10
        k = n % 10
        if n == i ** 3 + j ** 3 + k ** 3:
            print(n)
        i = n // 100
        j = n // 10 % 10
        k = n % 10
        if n == i*i*i + j*j*j + k*k*k: 
            print(n)
    

    运行效果:

    八、将一个正整数分解质因数

    🎈🎈🎈例如:输入90,打印出90=233*5
    答案:

    def reduceNum(n):
        if n in [1] :
            print ('{}'.format(n))
        while n not in [1] : 
            for index in range(2, n + 1) :
                if n % index == 0:
                    n //= index 
                    if n == 1: 
                        print (index )
                    else : 
                        print ('{} *'.format(index), end=" ")
                    break
    reduceNum(90)
    reduceNum(100)
    

    运行效果:

    九、统计

    🎈🎈🎈输入一行字符,分别统计出其中英文字母、空格、数字和其它字符的个数。

    s = input('')
    letters = 0
    space = 0
    digit = 0
    others = 0
    for c in s:
        if c.isalpha():
            letters += 1
        elif c.isspace():
            space += 1
        elif c.isdigit():
            digit += 1
        else:
            others += 1
    print ('char = %d,space = %d,digit = %d,others = %d' % (letters,space,digit,others))
    

    运行效果:

    十、求和

    🎈🎈🎈求s=a+aa+aaa+aaaa+aa…a的值,其中a是一个数字。例如2+22+222+2222+22222(此时共有5个数相加),几个数相加由键盘控制。

    答案:

    from functools import reduce
     
    Tn = 0
    Sn = []
    n = int(input('n = '))
    a = int(input('a = '))
    for count in range(n):
        Tn = Tn + a
        a = a * 10
        Sn.append(Tn)
        print (Tn)
     
    Sn = reduce(lambda x,y : x + y,Sn)
    print ("计算和为:",Sn)
    
    

    运行效果:

    ✨✨✨✨欢迎三连~~~~

    来源:不许代码码上红

    物联沃分享整理
    物联沃-IOTWORD物联网 » python练习题四

    发表评论