[CF1006F] Xor-Paths
Description
给出一个 n × m 的网格,每个格子上有权值 (a[i][j]),要从 (1,1) 走到 (n,m),每次只能向右或向下走,沿路计算异或和,求异或和等于 k 的路径数。
Solution
双向 BFS,由于要走的总步数为 (steps=n+m-2),正着走 (steps/2),反着走 ((steps+1)/2),然后合起来用 map 算答案即可
#include <bits/stdc++.h>
using namespace std;
#define int long long
const int N = 105;
int a[N][N], n, m, k;
signed main()
{
ios::sync_with_stdio(false);
cin >> n >> m >> k;
for (int i = 1; i <= n; i++)
{
for (int j = 1; j <= m; j++)
{
cin >> a[i][j];
}
}
int steps = n + m + 2;
map<pair<int, int>, int> mp;
vector<pair<int, int>> vec;
queue<tuple<int, int, int>> que;
que.push({1, 1, a[1][1]});
while (que.size())
{
auto [i, j, val] = que.front();
que.pop();
if (i + j == steps / 2)
{
mp[{i, val}]++;
}
else
{
if (i < n)
que.push({i + 1, j, val ^ a[i + 1][j]});
if (j < m)
que.push({i, j + 1, val ^ a[i][j + 1]});
}
}
que.push({n, m, a[n][m]});
while (que.size())
{
auto [i, j, val] = que.front();
que.pop();
if (i + j == steps / 2)
{
vec.push_back({i, val ^ a[i][j]});
}
else
{
if (i > 1)
que.push({i - 1, j, val ^ a[i - 1][j]});
if (j > 1)
que.push({i, j - 1, val ^ a[i][j - 1]});
}
}
int ans = 0;
for (auto [i, val] : vec)
{
ans += mp[{i, val ^ k}];
}
cout << ans << endl;
}