保姆级讲解 python之zip()方法实现矩阵行列转置

目录

  • 引入
  • 1.手动交换行列元素
  • 2.引入外部库
  • 进入正题
  • 使用列表推导式和zip()
  • 基本用法
  • 解压缩
  • 实现行列转置
  • 实战演练

  • 引入

    给你一个二维数组(矩阵),你怎么实现行列转置?
    在Python中,实现矩阵行列转置有多种方法


    1.手动交换行列元素

    通过遍历矩阵的每个元素,并将其放置到新位置来实现转置。

    示例实现:

    # 定义一个矩阵
    matrix = [[1, 2, 3], [4, 5, 6]]
    
    # 获取矩阵的行数和列数
    rows = len(matrix)
    cols = len(matrix[0])
    
    # 创建一个新的矩阵用于存放转置结果
    transposed_matrix = [[0 for _ in range(rows)] for _ in range(cols)]
    
    # 手动交换行列元素
    for i in range(rows):
        for j in range(cols):
            transposed_matrix[j][i] = matrix[i][j]
    
    print("原始矩阵:")
    for row in matrix:
        print(row)
    print("转置后的矩阵:")
    for row in transposed_matrix:
        print(row)
    '''
    原始矩阵:
    [1, 2, 3]
    [4, 5, 6]
    转置后的矩阵:
    [1, 4]
    [2, 5]
    [3, 6]
    '''
    


    2.引入外部库

    示例实现:

    import numpy
    
    # 定义一个矩阵
    matrix = numpy.array([[1, 2, 3], [4, 5, 6]])
    
    # 转置矩阵
    transposed_matrix = matrix.T
    
    print("原始矩阵:")
    for row in matrix:
        print(row)
    print("转置后的矩阵:")
    for row in transposed_matrix:
        print(row)
    '''
    原始矩阵:
    [1, 2, 3]
    [4, 5, 6]
    转置后的矩阵:
    [1, 4]
    [2, 5]
    [3, 6]
    '''
    

    太方便了我就要这个
    但是算法竞赛是不支持导入第三方库的,中道崩殂。
    那这么办?该zip()登场了


    进入正题

    使用列表推导式和zip()

    zip() 是 Python 内置的一个非常有用的功能,它用于将多个可迭代对象(如列表、元组等)组合在一起,然后返回一个由这些可迭代对象组成的元组的迭代器。
    每次迭代时,zip() 会从每个可迭代对象中取出一个元素,并把这些元素组合成一个新的元组。

    基本用法

    假设你有两个列表 a 和 b,你可以使用 zip(a, b) 来将它们配对:

    示例:

    a = ['a', 'b', 'c']
    b = [1, 2, 3]
    
    zipped = zip(a, b)
    print(list(zipped)) # 输出结果将会是:[('a', 1), ('b', 2), ('c', 3)]
    

    解压缩

    通过使用 * 操作符,可以解压之前用 zip() 组合的数据:

    示例:

    zipped = [('a', 1), ('b', 2), ('c', 3)]
    a, b = zip(*zipped)
    
    print(a)  # 输出: ('a', 'b', 'c')
    print(b)  # 输出: (1, 2, 3)
    

    实现行列转置

    zip(*matrix) 会将 matrix 的每一列作为新的子列表,从而实现矩阵的转置。操作符在这里用于解包矩阵的行,使每一行都作为一个独立的参数传递给 zip() 函数。这样,zip() 就可以将这些行重新组合成列了。

    示例:

    # 定义一个矩阵
    matrix = [[1, 2, 3], [4, 5, 6]]
    
    # 使用 zip() 进行转置
    transposed_matrix = [list(row) for row in zip(*matrix)]
    
    print("原始矩阵:")
    for row in matrix:
        print(row)
    print("转置后的矩阵:")
    for row in transposed_matrix:
        print(row)
    '''
    原始矩阵:
    [1, 2, 3]
    [4, 5, 6]
    转置后的矩阵:
    [1, 4]
    [2, 5]
    [3, 6]
    '''
    

    实战演练

    C-翻之 https://ac.nowcoder.com/acm/contest/100671/C


    这题思路同样非常关键,先来讲讲思路:

    题目要求我们决定是否通过翻转某一行来最大化全为1的列数。
    有点抽象,
    干脆我们假设答案为多个:第 j 列 和若干其他符合条件的列
    那么第 j 列肯定是全为1的列,其第 i 行必为1 ,没问题对吧
    那么同时其它符合条件的列第 i 行也必为1
    所以这些列可以说是同步变化的
    又因为任意一行的翻转必然会影响其他列,故只有当两列的字符串完全相同时,才会同步变化
    于是归纳为:符合条件的列为完全相同的列
    所以就考虑由列组成的字符串中出现次数最多的为这个最大值,即ans
    我们可以通过行列转置来得到这个列组成的字符串

    思路清晰了,来写code吧


    手动暴力转换发现超时

    from collections import defaultdict
    n, m = map(int, input().split())
    a=[]
    cnt=defaultdict(int)
    for _ in range(n):
        a.append(input())
    
    for j in range(m):
        s = ""
        for i in range(n):
            s+=a[i][j]
        cnt[s]+=1
    print(max(cnt.values()))
    

    又不支持导入第三方库,怎么办?
    那只能用它了 通过zip()实现

    附上题解code:

    from collections import defaultdict
    
    n, m = map(int, input().split())
    a = [input() for _ in range(n)]
    cnt = defaultdict(int)
    
    transposed_a = [row for row in zip(*a)]
    for row in transposed_a:
        cnt[row] += 1
    print(max(cnt.values()))
    


    不了解 默认字典defaultdict 可点此进入详细讲解


    END
    如果有更多问题或需要进一步的帮助,可以在评论区留言讨论哦!
    如果喜欢的话,请给博主点个关注 谢谢

    作者:查理零世

    物联沃分享整理
    物联沃-IOTWORD物联网 » 保姆级讲解 python之zip()方法实现矩阵行列转置

    发表回复