链接:B3611 【模板】传递闭包 - 洛谷
题目:
思路:
图论小知识+bitset优化
这一题其实就是一个 floyd 的板子题,我们主要学习 bitset 的用法
bitset 就是一个二进制数,但是我们能快速的更改指定位,同时又能像正常数字一样就行位运算
对于此题,我们可以直接利用 bitset 优化时间复杂度,降至 O(n²)
主要思想就是 或 运算和 图论小知识,对于 i,j,如果 i 能到达 j,那么 i 就能到达 j 也能到达的地方,利用这个小知识我们就能顺利解决问题了
和 floyd 一样,我们最外层枚举中间过度节点即可
代码:
#include <iostream>
#include <algorithm>
#include<cstring>
#include <iomanip>
#include<cctype>
#include<string>
#include <set>
#include <vector>
#include <cmath>
#include <queue>
#include <unordered_set>
#include <map>
#include <unordered_map>
#include <stack>
#include <utility>
#include <array>
#include <tuple>
#include <bitset>
using namespace std;
#define int long long
#define yes cout << "YES" << endl
#define no cout << "NO" << endl
int f[105][105];
int n;
bitset<105> a[105];
void solve()
{
cin >> n;
for (int i = 0; i < n; i++)
{
for (int j = 0; j < n; j++)
{
int x; cin >> x;
a[i][j] = x;
}
}
for (int i = 0; i < n; i++)
{
for (int j = 0; j < n; j++)
{
if (a[j][i])
{
a[j] |= a[i];
}
}
}
for (int i = 0; i < n; i++)
{
for (int j = 0; j < n; j++)
{
cout << a[i][j] << " ";
}
cout << endl;
}
}
void solve2()
{
cin >> n;
for (int i = 0; i < n; i++)
{
for (int j = 0; j < n; j++)
{
cin >> f[i][j];
}
}
for (int k = 0; k < n; k++)
{
for (int i = 0; i < n; i++)
{
for (int j = 0; j < n; j++)
{
f[i][j] |= f[i][k] & f[k][j];
}
}
}
for (int i = 0; i < n; i++)
{
for (int j = 0; j < n; j++)
{
cout << f[i][j] << " ";
}
cout << endl;
}
}
signed main()
{
//cin.tie(0)->sync_with_stdio(false);
int t = 1;
//cin >> t;
while (t--)
{
solve();
}
return 0;
}