首页 > 解决方案 > 查找给定矩阵转置的程序

问题描述

我在想找到矩阵转置的方法,下面是算法,但它没有给我正确的输出,所以任何人都可以告诉我我在哪里做错了,什么应该是正确的算法?我该如何改进它?

// m is the number of rows and n is the number of columns in a matrix
        for (int i = 0; i < m; i++) // For swapping the non-diagonal elements
        {
            for (int j = 0; j < n; j++)
            {
                if (i != j)
                {
                    int temp = 0;
                    temp = a[i][j];
                    a[i][j] = a[j][i];
                    a[j][i] = temp;
                }
            }
        }
        cout << "Elements of transpose matrix of a is: " << endl;
        for (int i = 0; i < m; i++) // printing the elements after transpose
        {
            for (int j = 0; j < n; j++)
            {
                cout << a[i][j] << " ";
            }
            cout << endl;
 



  

标签: c++matrix

解决方案


您在反转一维数组时犯了同样的错误,因此我将使用它作为一个更简单的示例:

#include <vector>
#include <iostream>
#include <utility>

std::vector<int> reverse_broken(std::vector<int> x){
    for (size_t i=0;i< x.size(); ++i){
        std::swap(x[i],x[x.size()-1-i]);
    }
    return x;
}

int main(){
    auto x = reverse_broken({1,2,3,4});
    for (const auto& e : x) std::cout << e << " ";
}

输出

1 2 3 4 

reverse_broken迭代所有元素并将它们与相应的反转元素交换。但是,一旦第一个与最后一个交换,最后一个已经交换。稍后将最后一个与第一个交换会使它们再次按原始顺序排列。

与您的转置相同。将对角线上方的元素与对角线下方的元素交换后,它们就已经转置了。您无需再次交换它们。

我将向您展示 的修复reverse_broken并留给您将相同的修复应用于您的转置:

std::vector<int> reverse(std::vector<int> x){
    for (size_t i=0;i< x.size()/2; ++i){
    // stop in the middle     ^^  because then all elements have been swapped
        std::swap(x[i],x[x.size()-1-i]);
    }
    return x;
}

您还应该考虑根本不转置矩阵。根据您访问交换元素的频率以及填充它的方式,从一开始就以正确的顺序填充它会更便宜,或者只是在访问时交换索引:

 // normal access: 
 auto x = a[i][j];
 // transposed access:
 auto y = a[j][i];

PS:我reverse仅用于说明。要反转容器,您实际上应该使用std::reverse. 另请注意,您可以而且应该使用std::swap. 最后但并非最不重要的一点是,只有一个方阵可以就地转置。对于非方阵,您需要构建一个具有不同维度的新矩阵。


推荐阅读