【问题标题】:Maximum in column of 2d array using divide and conquer使用分而治之的二维数组列中的最大值
【发布时间】:2016-12-25 23:52:57
【问题描述】:

假设我们有一个二维数组

1   2    3   1
5   6    4   0
0   3    2   1 
1   2    1   0

如果每行的行长不同,是否有一种全局方法如何使用分治技术在列中找到最大数量?

我指的是在需要此步骤的二维数组中查找峰值的步骤。

在一维数组上会是这样的

int maxNumber( vector<int> a , int min , int max ){
    if( min == max )
        return a[min];
    int mid = ( min + max)/2;
    int i   = maxNumber( a , min , mid );
    int j   = maxNumber( a , mid +1, max);
    if( i > j)
        return i;
    return j;
    } 

   vector<int> v = { 1 , 2 , 5 , 0 , 10 , 9};
   cout << maxNumber( a , 0 , a.size() -1 );

现在对于 NxN 或 NxM 矩阵,我们可以做

int maxNumberCollum( vector<vector<int>> a , int row_min , int row_max , int size){
    if ( row_min == row_max ){
        return a[row_min][size];
    }

    int row = ( row_min + row_max ) / 2;
    int i   = maxNumberCollum( a , row_min , row     , size );
    int j   = maxNumberCollum( a , row + 1 , row_max , size);

    if( i > j)
        return i;
    return j;
};

 vector< vector<int> > a = { { 1 , 2 , 3 },
                             { 5 , 0 , 1 },
                             { 6 , 2 , 0 }
                           };
cout << maxNumberCollum( a , 0 , a.size() -1 , 2 )

我们希望在作为参数传递的列中找到最大值。

但是考虑到我们不知道矩阵(二维数组)是否为 NxN / NxM 或者每一行的行长不同,如何将其实现为二维数组的有效方法是什么?

【问题讨论】:

  • 对每一列做一维案例,然后对每一列的结果再做一维案例?
  • 必须使用 D&C 来解决您的问题吗?
  • @shole 这不是必须的,但我试图用 D&C 来解决这个问题
  • 错字提醒:它是一个 - 不是“列”..
  • (标题中的in column 和这篇文章的第一个问题是什么?with column we want to find maximum in passed as argument. 是什么意思?)

标签: c++ arrays algorithm containers divide-and-conquer


【解决方案1】:

由于每个向量都有自己的大小,您可以使用该信息来查找每行中的最大数量。

你有这条线的地方:

return a[row_min][size];

将其替换为对 1d 函数的调用:

return maxNumber(a[row_min], 0, a[row_min].size() - 1)

【讨论】:

  • 这实际上会引发不好的结果。另外,再次调用 log n 函数不会使渐近复杂度高很多吗?
  • 您必须查看每个值以在任何情况下找到最大值,因此您将始终具有 NXM 复杂性。我不明白为什么它会抛出一个不好的结果,这是一个太模糊的描述 - 你应该使用调试器。此外,正如您在此处所做的那样,按值传递向量将导致制作额外的副本。通过引用传递向量可能更可取。
  • 请注意,您可以只做一个简单的嵌套循环,而不是分而治之。
【解决方案2】:

如果您考虑一个由不同大小的向量组成的向量,关键是要确保您不会尝试访问超出其范围的那些。

例如,考虑以下代码:

#include <iostream>
#include <vector>
#include <limits>

using std::cout;
using std::vector;

const int lowest_int = std::numeric_limits<int>::lowest();

int max_number_in_column( const vector<vector<int>> &a, 
                          size_t row_min, size_t row_max, size_t col)
{
    if ( row_min == row_max ) {
        return col < a[row_min].size() ? a[row_min][col] : lowest_int;
    }

    int row = ( row_min + row_max ) / 2;
    int i   = maxNumberColumn( a, row_min, row,     col);
    int j   = maxNumberColumn( a, row + 1, row_max, col);

    return i > j ? i : j;
};

int main() {
    vector<vector<int>> a = {
        { 1 , 2 , 3 },
        { 5 , 0 , 1, -8 },
        { 6 , 2 }
    };

    size_t col = 3;
    int max = max_number_in_column(a, 0, a.size() - 1, col);

    if ( max > lowest_int ) 
        cout << "The greater element of column " << col << " is " << max <<'\n';
    else
        cout << "Unable to find a maximum value in column " << col << '\n';

    return 0;
}

我真的不明白为什么你要尝试使用分而治之的技术来做到这一点,而使用通用循环会更容易:

int max_number_in_column( const vector<vector<int>> &a , size_t col)
{
    int max = lowest_int;
    for ( auto const &row : a ) {
        if ( col < row.size()  &&  row[col] > max ) max = row[col];
    }
    return max;
};

【讨论】:

    猜你喜欢
    • 2017-01-12
    • 2013-01-16
    • 2019-11-05
    • 2016-10-16
    • 2017-06-07
    • 2018-03-10
    • 2016-05-01
    • 2017-02-17
    • 2021-11-27
    相关资源
    最近更新 更多