【问题标题】:The fastest algorithm for returning max length of consecutive same value fields of matrix?返回矩阵的连续相同值字段的最大长度的最快算法?
【发布时间】:2014-10-21 16:16:38
【问题描述】:

这是给定的示例:

我们有一个函数,它接受一个矩阵,它的列数和行数并返回 int(这将是长度)。例如:

     int function (int** matrix, int n, int m)

问题是实现此函数的最快算法是什么,因此它返回具有相同值的连续字段的最大长度(这些相同的值是在一列还是一行中并不重要,在图片上的这个例子中它是一列的 5 个字段,值为 8)? 值可以是 0-255(例如灰度)。 所以在给定的示例函数中应该返回 5。

【问题讨论】:

    标签: algorithm matrix


    【解决方案1】:

    如果这是一个瓶颈并且矩阵很大,则尝试的第一个优化是按顺序内存顺序(C 或 C++ 中的逐行)而不是两次遍历矩阵。这是因为在另一个方向遍历二维数组非常昂贵。缓存和分页行为是最糟糕的。

    为此,您将需要一个行大小的数组来跟踪每列中当前运行中连续值的数量。

    int function (int a[][], int m, int n) {
      if (n <= 0 || m <= 0) return 0;
    
      int longest_run_len = 1; // Accumulator for the return value.
      int current_col_run_len[n]; // Accumulators for each column
      int current_row_run_len = 1; // Accumulator for the current row.
    
      // Initialize the column accumulators and check the first row.
      current_col_run_len[0] = 1;
      for (int j = 1; j < n; j++) {
        current_col_run_len[j] = 1;
        if (a[0][j] ==  a[0][j-1]) {
          if (++current_row_run_len > longest_run_len)
            longest_run_len = current_row_run_len;
        } else current_row_run_len = 1;
      }
    
      // Now the rest of the rows...
      for (int i = 1; i < m; i++) {
    
        // First column:
        if (a[i][0] == a[i-1][0]) {
          if (++current_col_run_len[0] > longest_run_len)
            longest_run_len = current_col_run_len[0];
        } else current_col_run_len[0] = 1;
    
        // Other columns.
        current_row_run_len = 1;
        for (int j = 1; j < n; j++) {
          if (a[i][j] == a[i][j-1]) {
            if (++current_row_run_len > longest_run_len)
              longest_run_len = current_row_run_len;
          } else current_row_run_len = 1;
          if (a[i][j] == a[i-1][j]) {
            if (++current_col_run_len[j] > longest_run_len)
              longest_run_len = current_col_run_len[j];
          } else current_col_run_len[j] = 1;
        }
      }
      return longest_run_len;
    }
    

    【讨论】:

      【解决方案2】:

      您需要至少传递矩阵的每个条目一次,因此您不可能做得比 O(m*n) 更好。

      最直接的方法是对每一行每一列都传递一次。这将是两次遍历矩阵,但算法仍然是 O(m*n)。

      任何一次尝试都可能会复杂得多。

      int function (int** matrix, int n, int m) {        
          int best=1;
          for (int i=0; i<m; ++i) {
              int k=1;
              int last=-1;
              for (int j=0; j<n; ++j) {
                  if (matrix[i][j] == last) {
                       k++;
                       if (k > best) {
                           best=k;
                       }
                  } 
                  else {                     
                       k=1;
                  }
                  last = matrix[i][j];
              }
           }
           for (int j=0; j<n; ++j) {
              int k=1;
              int last=-1;
              for (int i=0; i<m; ++i) {
                  if (matrix[i][j] == last) {
                       k++;
                       if (k > best) {
                           best=k;
                       }
                  } 
                  else {                     
                       k=1;
                  }
                  last = matrix[i][j];
              }
           }
           return best;
      }
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2021-11-27
        • 1970-01-01
        • 2021-11-25
        • 2021-11-26
        • 2023-04-11
        • 2021-10-01
        相关资源
        最近更新 更多