這道題目一開始看的時候沒有思路,但是看到資料範圍裡面有乙個:
\(m = n-1\) 或 \(m = n\) ,一下子有了思路。
當 \(m = n-1\) 時,這就是一棵樹,以1為根節點進行搜尋,每次優先訪問編號小的點即可。
當 \(m = n\) 時,可知只有乙個環,找到環中對應的所有邊,然後遍歷每一條環中的邊,假設刪除它,然後就變成了一棵樹。
時間複雜度為:\(o(n^2)\) 。
實現**如下:
#include using namespace std;
const int maxn = 5050;
struct node
node(int _u, int _v, int _id)
} edge[maxn*2], loop_edge[maxn];
vectorg[maxn];
int n, m, p[maxn], pe[maxn], cnt, depth[maxn];
bool vis[maxn], vise[maxn*2], marked[maxn*2];
int ans_seq[maxn], tmp_seq[maxn], ans_cnt, tmp_cnt;
bool cmp(node a, node b)
void find_loop(int u, int pre, int d) }}
void select_loop_edges(int u, int v, int id)
else if (depth[u] < depth[v])
else }}
void dfs(int u, int pre)
}void final_check()
else if (ans_seq[i] < tmp_seq[i]) break;
} }else
flag = true;
if (flag) for (int i = 0; i < n; i ++) ans_seq[i] = tmp_seq[i];
}int main()
for (int i = 1; i <= n; i ++) sort(g[i].begin(), g[i].end(), cmp);
if (m == n)
} for (int i = 0; i < cnt; i ++)
} else
for (int i = 0; i < n; i ++)
puts("");
return 0;
}
洛谷 P5022 旅行
傳送門 給出乙個有n nn個點的圖,一共有m mm雙向邊,求如何走能使得走到的點按先後順序字典序最小 對於前60 60 60 的資料來說,直接暴力dfs dfsdf s即可而其他的點,則根據基環樹的性質,將每條邊列舉刪去,剩下的肯定是棵樹 進而就得到了類似於60 60 60 的資料的情況 inclu...
洛谷 P5022 旅行
day2就藍題起步不是要我命嗎 目測資料 不都是基環樹和樹嘛?基環樹我不會但是這個樹的貪心不是裸的嗎?大手一揮 這部分分我打定了!int outp 5100 len void dfs int x,int fa void main 光榮地水到了60分 對於剩下的分,我們來好好觀察一下題面 n 5000...
洛谷 P5022 旅行(DFS 斷環)
首先對於m n 1的情況非常好想 即這是一棵樹,然後從1節點開始,搜一遍。注意要搜出來的序列的字典序最小,所以用鄰接矩陣來儲存,存的時候按當前節點能到的節點的編號從小到大排序。當m n的時候 這時候便是乙個基環樹,在樹上的某乙個地方會有乙個環,會發現環上的有一條邊是不會走的。然而並不確定這條邊到底是...