這道題正解其實是lct,然而貌似spfa也可以成功水過,所以根本不知道lct的我只能說spfa了。
這道題最大的限制是兩種精靈就意味著一條道可能有兩個權值,因此我們需要去將其中乙個固定,然後再推另乙個權值,也就是說,我們可以,列舉每一條邊的a,然後只走a值不大於他的邊。
然而並沒有那麼容易,本題資料極大,這種演算法一半分都拿不到,因此我們需要別的優化,首先,我們可以現將每個邊按照a的大小進行排序,然後從小到大邊列舉邊加邊,這時dis陣列就不必去每次spfa都清空了,而且每次列舉邊都可以在原來的圖的基礎上直接加邊,且當前邊一定都是能走的邊,不必再算上那些不滿足要求的邊了,可以大大地優化是時間複雜度。
1 #include2 #include3 #include4 #include5 #include6 #include7 #include8 #includeview code9 #include10
using
namespace
std;
11int n,m,zz,a[500005
];12
struct
roroad[2000005
];17
struct
nonode[200004
];20
void build(int x,int y,int z,int
zx)21
30int dis[500005
];31 queueq1;
32bool rd[500005
];33
int ans=0x7fffffff;34
void spfa(int x0,int y0,int z,int
zx)55}56
}57}58
int an=0
;59 an=dis[n];
60if(an!=dis[0]&&ans>an+z)
61 ans=an+z;62}
63int
px(no a,no b)
6467
intmain()
79 sort(node+1,node+m+1
,px);
80 dis[1]=0,rd[1]=1
;81 q1.push(1
);82
for(int i=1;i<=m;i++)
8389
if(ans==0x7fffffff) ans=-1
;90 printf("
%d\n
",ans);
91//
while(1);
92return0;
93 }
NOI2014 魔法森林
為了得到書法大家的真傳,小e同學下定決心去拜訪住在魔法森林中的隱士。魔法森林可以被看成乙個包含個n節點m條邊的無向圖,節點標號為 1 n 邊標號為1 m 初始時小e同學在 1 號節點,隱士則住在 n 號節點。小e需要通過這一片魔法森林,才能夠拜訪到隱士。魔法森林中居住了一些妖怪。每當有人經過一條邊的...
NOI2014 魔法森林
為了得到書法大家的真傳,小 e 同學下定決心去拜訪住在魔法森林中的隱士。魔法森林可以被看成乙個包含 n 個節點 m 條邊的無向圖,節點標號為1,2,3,n,邊標號為 1,2,3,m。初始時小 e 同學在 1 號節點,隱士則住在 n 號節點。小 e 需要通過這一片魔法森林,才能夠拜訪到隱士。魔法森林中...
NOI2014 魔法森林
noi2014 魔法森林 要求a 與 b 的總和最小 可以按a排序 再以b為權值維護一顆樹 lct維護最小生成樹 要解決的問題 將每一條邊變為乙個點 邊權變為點權 舉個栗子 u v有一條邊權為w的邊 怎lct連邊方式為 u new v new的點權為w 不斷維護最小生成樹 如果新加入的邊的 u與v不...