矩阵中最长的子序列

时间:2016-09-24 23:03:19

标签: algorithm matrix dynamic lcs

我有一个像这样的矩阵 - >

1 6 2
8 3 7
4 9 5

你可以向任何方向,在对角线上向左下方,你必须找到最长的子序列,你可以选择序列中的下一个数字,使其绝对差值大于3.

与上面的情况类似,最长的子序列是1->6->2->7->3->8->4->9->5

我能为它写一个强力代码,找到最长的序列,就像找到第一个数字,第二个数字等的最长序列一样。并返回具有最大计数的那个。

我是DP新手。有没有其他方法可以通过使用DP来解决这个问题?我无法理解使用DP的解决方案。

1 个答案:

答案 0 :(得分:3)

N为行数,M为列数。

您可以尝试使用状态的动态编程方法: dp(int row_idx, int col_idx, int visited_msk)其中visited_msk是一个表示到目前为止访问过的单元格的整数(即matrix[i][j] visited_msk中的ID将为i*M + j

在你的DP中,你将迭代相邻的8个单元格(如果它们在边界内)并且只有当绝对差值大于3并且没有像这样访问单元格时才从当前单元格调用DP:< / p>

让掩码中的新索引为new_idx = new_row_idx * M + new_col_idx 在内部循环中,条件将是这样的:

if(abs(matrix[row_idx][col_idx] - matrix[new_row_idx][new_col_idx]) > 3 && !((visited_msk >> new_idx) & 1)) {
  result = max(result, dp(new_row_idx, new_col_idx, visited_msk | (1<<new_idx)) + 1);
}

这种方法的顺序是O(2 ^(N * M)* N * M * 8),因此如果N * M(网格大小)<= 15,它将会很好。