P1613 跑路
作者:互联网
P1613 跑路
题意
已知一个每秒可以移动 2k 距离,k 任意
给出一个有向图,上限 50 个点,10000 条有向边
请问从 1 到 n 所需的最少时间
思路
由于与 2k 次方有关,所以可以像 ST 表一样处理
用 dp[i][j][k] 表示 i 与 j 之间距离为 2k 的路径是否存在
for (int l = 1; l <= 64; l++)
for (int k = 1; k <= n; k++)
for (int i = 1; i <= n; i++)
for (int j = 1; j <= n; j++)
dp[i][j][l] |= (dp[i][k][l - 1] & dp[k][j][l - 1]);
代码
#include <bits\stdc++.h>
using namespace std;
const int maxn = 100;
const int inf = 0X3f3f3f3f;
bool dp[maxn][maxn][maxn];
int a[maxn][maxn];
int main()
{
// ios::sync_with_stdio(false);
// cin.tie(nullptr);
// cout.tie(nullptr);
int n, m;
cin >> n >> m;
int u, v;
for (int i = 1; i <= m; i++) {
cin >> u >> v;
dp[u][v][0] = true;
}
for (int l = 1; l <= 64; l++)
for (int k = 1; k <= n; k++)
for (int i = 1; i <= n; i++)
for (int j = 1; j <= n; j++)
dp[i][j][l] |= (dp[i][k][l - 1] & dp[k][j][l - 1]);
for (int i = 1; i <= n; i++)
for (int j = 1; j <= n; j++)
for (int k = 1; k <= 64; k++)
dp[i][j][0] |= dp[i][j][k];
memset(a, 0X3f, sizeof(a));
for (int i = 1; i <= n; i++)
for (int j = 1; j <= n; j++)
if (dp[i][j][0])
a[i][j] = 1;
for (int k = 1; k <= n; k++)
for (int i = 1; i <= n; i++)
for (int j = 1; j <= n; j++)
a[i][j] = min(a[i][j], a[i][k] + a[k][j]);
cout << a[1][n] << '\n';
return 0;
}
标签:const,2k2,int,k2k,maxn,P1613,dp 来源: https://blog.csdn.net/qcwlmqy/article/details/102721124