前者之所以叫加强版,就是把uva1027改编了,附加上打印路径罢了。

03年的final题哦!!虽然是水题,但不是我这个只会做图论题的跛子能轻易尝试的——因为有个数学坑。

题意:运送x个货物从a->b,沿途要上交过路费,village(小写字母)只需交一个单位的货物,town(大写字母)要交(x/20+((x%20==0)?0:1))个单位的货物,即每20个货物要上交一个,不足的按20处理。现在已知要送到b点y个货物,那么最少从x出发要携带多少个货物。

注意:

1、路过town:19=20-1,同时19=21-2,所以要求最小值。

2、用dijkstra做,不过是从 b->a ,路径u->v的权值为经过u点扣除的货物。

3、打印路径:反向。从a->b,沿着d[v]==d[u]-s走,必为最短路。(从b->a有多条最短路,但从a->b沿着这个条件走,只有一条最短路)

4、字典序最小:预处理,sort()后再建图。已知邻接表是模仿指针的头插法——后进先出。

5、数学坑= =:

  先举个例子,要送到town A 10000个货物,针对10000,要扣除500。那么是不是携带10500就能满足要求呢?不是的T^T,10500-525==9975。所加上的500,仍然会被扣除一些货物。(TLE的原因,本以为差的不多,就每次做++判断了)

  用递推直接求每部分要补充的货物,用大数据测发现差了1。这不是计算问题,而是存在错误的:沿用上一个例子,要送10000个货物,需扣除500个,500又需扣25个,那么25需不需要扣呢?扣的话又要扣2个,那么两个还要再扣一个么??关键是余数,两次扣除的余数均不为0,那么分开算要扣2个,然而两数之和不足20,只需扣1个。

  所以要直接求。

6、不要忘了long long,__int64 害我CE了一发

 #include<cstdio>
#include<cstring>
#include<queue>
#include<vector>
#include<algorithm>
#define LL long long
using namespace std; const int MAXN=;
const LL INF =1e12+; struct Edge{
int v,next;
Edge(){}
Edge(int _v,int _next):v(_v),next(_next){}
}edge[MAXN*MAXN]; struct N{
int l,r;
}a[MAXN*MAXN]; int cmp(N a,N b)
{
if(a.l==b.l)
return a.r>b.r;
return a.l<b.l;
} int head[MAXN],tol;
int vis[MAXN];
LL d[MAXN];
queue<int>q; void init()
{
tol=;
memset(head,-,sizeof(head));
} void add(int u,int v)
{
edge[tol]=Edge(v,head[u]);
head[u]=tol++;
} void dijkstra(int st,int c)
{
memset(vis,,sizeof(vis));
for(int i=;i<;i++)
if(i==st)d[i]=c;
else d[i]=INF;
for(int i=;i<;i++)
{
if(head[i]==-)
continue; int x;
LL m=INF;
for(int j=;j<;j++)
{
if(!vis[j]&&d[j]<m){
x=j;
m=d[x];
}
}
vis[x]=;
LL t=,p=d[x];
if(x<)
while((p+t)-(p+t)/-((p+t)%==?:)<d[x])
{
t+=d[x]-((p+t)-(p+t)/-((p+t)%==?:));
}
else
t=;
for(int j=head[x];j!=-;j=edge[j].next)
{
int v=edge[j].v; if(d[v]>d[x]+t){
d[v]=d[x]+t;
}
}
}
} void road(int st,int ed)
{
int u=st;
LL s;
while(u!=ed)
{
for(int i=head[u];i!=-;i=edge[i].next)
{
int v=edge[i].v;
if(v<)
s=d[u]/+((d[u]%==)?:);
else
s=;
if(d[v]==d[u]-s){
q.push(v);
u=v;
break;
}
}
}
while(!q.empty())
{
int v=q.front();q.pop();
if(v<)
printf("-%c",v+'A');
else
printf("-%c",v-+'a');
}
printf("\n");
} int num(char ch)
{
if('a'<=ch&&ch<='z')
return (+ch-'a');
else
return (ch-'A');
} int main()
{
int n,c,cnt=;
char str1[],str2[];
while(~scanf("%d",&n))
{
if(n==-)
return ;
init();
for(int i=;i<n;i++)
{
scanf("%s%s",str1,str2);
a[i].l=num(str1[]);
a[i].r=num(str2[]);
}
sort(a,a+n,cmp);
for(int i=;i<n;i++)
{
add(a[i].l,a[i].r);
add(a[i].r,a[i].l);
} scanf("%d%s%s",&c,str1,str2);
int x=num(str1[]);
int y=num(str2[]);
dijkstra(y,c); printf("Case %d:\n",cnt++);
printf("%lld\n",d[x]);
if(x<)
printf("%c",x+'A');
else
printf("%c",x-+'a');
road(x,y);
}
return ;
}
 a b
b c
a d
d c
a c A B
B C
C D
D E
E F
F G
G H
H I
I J
J K
K L
L M
M N
N O
O P
P Q
Q R
R S
S T
T U
U V
V W
W X
X Y
Y Z
Z a
a b
b c
c d
d e
e f
f g
g h
h i
i j
j k
k l
l m
m n
n o
o p
p q
q r
r s
s t
t u
u v
v w
w x
x y
y z
A z A b
A B
b c
B c
A c A b
A B
b c
B c
A c A D
D X
A b
b c
c X
A X -

input

 Case :

 a-b-c

 Case :

 A-B-C-D-E-F-G-H-I-J-K-L-M-N-O-P-Q-R-S-T-U-V-W-X-Y-Z-a-b-c-d-e-f-g-h-i-j-k-l-m-n-o-p-q-r-s-t-u-v-w-x-y-z

 Case :

 A-B-c

 Case :

 A-b-c

 Case :

 A-b-c-X

output

唉,吐槽一下。谁调试不用数据,就不能共享一下?做图论整天挨卡,想找个数据都找不到,自己又造不出好数据,要不然昨天那道lca就不会枚举344组数据了。当然,偶也知道debug的能力是重中之重,但这是经验积累起来的,以我这种弱菜,去刷uva&LA这种连题解都找不到的题库,受老咔哒了。难怪队友都说我整天愁眉苦脸的= =

UVA 10537 The Toll! Revisited uva1027 Toll(最短路+数学坑)的更多相关文章

  1. UVA 10537 The Toll! Revisited 过路费(最短路,经典变形)

    题意:给一个无向图,要从起点s运送一批货物到达终点e,每个点代表城镇/乡村,经过城镇需要留下(num+19)/20的货物,而经过乡村只需要1货物即可.现在如果要让p货物到达e,那么从起点出发最少要准备 ...

  2. UVA 10537 - The Toll! Revisited(dijstra扩张)

    UVA 10537 - The Toll! Revisited option=com_onlinejudge&Itemid=8&page=show_problem&catego ...

  3. uva 10537 Toll! Revisited(优先队列优化dijstra及变形)

    Toll! Revisited 大致题意:有两种节点,一种是大写字母,一种是小写字母. 首先输入m条边.当经过小写字母时须要付一单位的过路费.当经过大写字母时,要付当前財务的1/20做过路费. 问在起 ...

  4. UVA10537 Toll! Revisited

    difkstra + 路径输出 The Toll! Revisited Time Limit: 3000MS Memory Limit: Unknown 64bit IO Format: %lld & ...

  5. UVA 816 -- Abbott's Revenge(BFS求最短路)

     UVA 816 -- Abbott's Revenge(BFS求最短路) 有一个 9 * 9 的交叉点的迷宫. 输入起点, 离开起点时的朝向和终点, 求最短路(多解时任意一个输出即可).进入一个交叉 ...

  6. 【Toll!Revisited(uva 10537)】

    题目来源:蓝皮书P331 ·这道题使得我们更加深刻的去理解Dijkstra!       在做惯了if(dis[u]+w<dis[v])的普通最短路后,这道选择路径方案不是简单的比大小的题横在了 ...

  7. UVa 10537 The Toll! Revisited (最短路)

    题意:给定一个图,你要从 s 到达 t,当经过大写字母时,要交 ceil(x /20)的税,如果经过小写字母,那么交 1的税,问你到达 t 后还剩下 c 的,那么最少要带多少,并输出一个解,如果多个解 ...

  8. The Toll! Revisited UVA - 10537(变形。。)

    给定图G=(V,E)G=(V,E),VV中有两类点,一类点(AA类)在进入时要缴纳1的费用,另一类点(BB类)在进入时要缴纳当前携带金额的1/20(不足20的部分按20算) 已知起点为SS,终点为TT ...

  9. UVA 10537 Toll! Revisited (逆推,最短路)

    从终点逆推,d[u]表示进入u以后剩下的货物,那么进入u之前的货物数量设为y,d[u] = x,那么y-x=ceil(y/20.0)=(y-1)/20+1=(y+19)/20. (y-x)*20+r= ...

随机推荐

  1. 2007: [Noi2010]海拔 - BZOJ

    Description YT市是一个规划良好的城市,城市被东西向和南北向的主干道划分为n×n个区域.简单起见,可以将YT市看作一个正方形,每一个区域也可看作一个正方形.从而,YT城市中包括(n+1)× ...

  2. c++ switch case

    http://www.cnblogs.com/RealOnlyme/articles/2579628.html

  3. Leetcode#78 Subsets

    原题地址 有两种方法: 1. 对于序列S,其子集可以对应为一个二进制数,每一位对应集合中的某个数字,0代表不选,1代表选,比如S={1,2,3},则子集合就是3bit的所有二进制数. 所以,照着二进制 ...

  4. intellij idea 14 ULTIMATE 注册码

    Name:happy KEY:63763-YCO0I-QR4TV-G4I3E-4XGK9-GQSQ3

  5. 腾讯QQ企业邮箱在ruby on rails 框架中的mailer配置

    在编写ruby on rails程序时,我们可能会需要用到发送邮件的程序,如果使用gmail进行smtp发送一般问题不大,但很多企业使用的是腾讯QQ企业邮箱.使用该邮箱进行链接时出现各种错误,goog ...

  6. PHP之preg_replace()与ereg_replace()正则匹配比较讲解

    <?php //preg_replace()和ereg_replace()函数的使用的比较 // -------preg_replace()-------------------------- ...

  7. 01-03-02-2【Nhibernate (版本3.3.1.4000) 出入江湖】CRUP操作-Save方法的一些问题

    此文由于当时不知道NHibernate的Sava方法不是更新操作,不知道Save就是Add,造成如下荒唐的求证过程,但结论是对的 ,可报废此文,特此声明. NHibernate--Save方法: Cu ...

  8. php浮点数精确运算

    php浮点数精确运算 Php: BCMath bc是Binary Calculator的缩写.bc*函数的参数都是操作数加上一个可选的 [int scale],比如string bcadd(strin ...

  9. package.json 字段全解析 share

    Name 必须字段. 小提示: 不要在name中包含js, node字样: 这个名字最终会是URL的一部分,命令行的参数,目录名,所以不能以点号或下划线开头: 这个名字可能在require()方法中被 ...

  10. hdu 3441 Rotation

    总的来说,这题要2次用到polya定理. 由题目条件A*A=B*B+1,变形为(A-1)*(A+1)=K*B*B; 分别分解A-1和A+1的质因数,在合并在一起. 第一步:搜索B,对B*B的正方形涂色 ...