70分做法:
先預處理出所有點的最近和次近(o(n^2)一遍就ok)
然後暴力求出每個解(o(nm))
//by siriusren
#include
#include
#include
#define inf 0x3fffffff
using
namespace
std;
int n,x,rech=0x3fffffff,rec,s,m;
double ans=0x3fffffff;
struct path}path[100050];
struct nodenode[100050];
bool cmp(node a,node b)
for(int i=1;i<=n;i++)
else
if(path[i].weight2==abs(node[j].height-node[i].height)&&node[j].heightif(path[i].weight2else
if(path[i].weight2==path[i].weight&&node[j].heightscanf("%d",&x);
for(int i=1;i<=n;i++)
else
f^=1;
}if(wei1&&(ans>1.0*wei2/wei1||(ans==1.0*wei2/wei1&&rech1.0*wei2/wei1;
rec=i;
rech=node[i].height;}}
printf("%d\n",rec);
scanf("%d",&m);
for(int i=1;i<=m;i++)
else
f^=1;
}printf("%d %d\n",wei2,wei1); }}
100分做法:
先用set 從後向前插入 ,取出左邊兩個點和右邊兩個點(如果有的話),排個序。
o(nlogn)求出最近和次近。
然後呢 用倍增求距離
g[i][j]表示從i出發走2^j輪到的地方
f[i][j][0]表示從i出發走2^j輪a走了多少
f[i][j][1]表示從i出發走2^j輪b走了多少
預處理出走一輪到哪兒
g[i][0]=edge[edge[i].to2].to;
f[i][0][0]=edge[i].weight2;
f[i][0][1]=edge[edge[i].to2].weight;
倍增就好了…
NOIP 2012 Senior 3 開車旅行
還是太弱了 這道題拿到手上後完全沒有能夠在規定時間內解決的思路。不過還好,大體思路是對的 首先預處理a b在每個地方開一次車到達的地方。對於第一問,列舉a出發的位置,對於第二問,直接計算就行了。計算的方法就是挨著推,直到滿足題目中結束旅行的條件。很明顯,預處理的時間複雜度為o n2 計算的時間複雜度...
NOIp2012 開車旅行
傳送門 以後序列上的問題可以想一想倍增。s a i s b i sa i sb i sa i sb i 記錄在i ii這個位置讓a b a ba b開車到達的點。把a aa和b bb都跳一次稱為一輪。d is i j dis i j dis i j 表示從i ii跳2 j2 j 2j輪的總路程。p ...
Noip2012 開車旅行
小 a 和小 b 決定利用假期外出旅行,他們將想去的城市從 1 到 n 編號,且編號較小的城市在編號較大的城市的西邊,已知各個城市的海拔高度互不相同,記城市 i 的海拔高度為hi,城市 i 和城市 j 之間的距離 d i,j 恰好是這兩個城市海拔高度之差的絕對值,即d i,j hi hj 旅行過程中...