

题意:
给定 两个矩阵,矩阵 a 大小为 h1 行 w1 列,矩阵 b 大小为 h2 行 w2 列。
h1 >= h2, 且 w1 >= w2。
判断 对矩阵 a 进行有限次 删行、删列 操作 能否转化成 矩阵 b。
如果 能够办到,则 输出 “Yes”,否则 输出 “No”。
思路
将 删行列 转化为 保留行列,
设置 两个 dfs,前者负责 枚举准备保留的行,后者 枚举准备保留的列,
在 第一个 dfs 选择了 h2 行 进行 保留 之后,进行 第二个 dfs 选择 w2 列 进行 保留,
每搜到一个 从第一个矩阵 a 保留 h2 行、w2 列之后 转化而来的 与第二个矩阵 b 大小相等 的 矩阵 c 之后,判断 c 是否与 b 完全相等,
如果 相等,则 表示 a 矩阵可以通过若干次删行或删列操作转化为 b 矩阵 输出 “Yes”,否则,输出 “No”。
代码:
#include <bits/stdc++.h>
using namespace std;
//#define map unordered_map
//#define int long long
const int N = 15;
int h1, w1, h2, w2;
int a[N][N], b[N][N], row[N], col[N];
int idx1, idx2;
void dfs2(int start) //保留哪些列
{
if (idx1 == w2)
{
int tot1 = 0, tot2 = 0;
for (int i = 1; i <= h2; ++i)
{
++tot1, tot2 = 0;
for (int j = 1; j <= w2; ++j)
{
int r = row[tot1], c = col[++tot2];
if (a[r][c] != b[i][j]) return; //如不相等,搜下一个分支
}
}
puts("Yes"); //相等输出yes 直接强制结束所有程序(注意是所有)
exit(0);
}
if (start == w1) return;
dfs2(start + 1);
for (int i = start + 1; i <= w1; ++i)
{
col[++idx1] = i; //把保留的列加入数组
dfs2(i);
--idx1;
}
}
void dfs1(int start) //保留哪些行
{
if (idx2 == h2)
{
dfs2(0);
return;
}
if (start == h1) return;
//不删
dfs1(start + 1);
//删
for (int i = start + 1; i <= h1; ++i)
{
row[++idx2] = i; //把保留的行加入一个数组
dfs1(i);
--idx2;
}
}
signed main()
{
cin >> h1 >> w1;
for (int i = 1; i <= h1; ++i)
{
for (int j = 1; j <= w1; ++j)
{
cin >> a[i][j];
}
}
cin >> h2 >> w2;
for (int i = 1; i <= h2; ++i)
{
for (int j = 1; j <= w2; ++j)
{
cin >> b[i][j];
}
}
dfs1(0);
puts("No");
}

本文介绍了一种使用深度优先搜索(DFS)算法解决矩阵转换问题的方法。通过递归地选择保留的行列来尝试将一个矩阵转化为另一个矩阵。若成功转化则输出“Yes”,否则输出“No”。涉及数组、递归和矩阵比较等内容。
802

被折叠的 条评论
为什么被折叠?



