summary:14

1.k短路

2.tarjan缩无向图点

3.复习了SA

4.差分约束

5.求第二短路

洛谷3824:dfs优化背包。开始的时候mle了,然后我就把a[i],w[i]去掉。。。。就A了。优化空间。。。

#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
using namespace std;
#define rep(i,s,t) for(int i=s;i<=t;i++)
#define dwn(i,s,t) for(int i=s;i>=t;i--)
#define clr(x,c) memset(x,c,sizeof(x))
int read(){
int x=0;char c=getchar();
while(!isdigit(c)) c=getchar();
while(isdigit(c)) x=x*10+c-'0',c=getchar();
return x;
}
const int nmax=10000005;
int sum[nmax],cnt[nmax],ans=0,n,m;
void maxs(int &a,int b){
if(a<b) a=b;
}
void dfs(int cur,int x,int y){
if(sum[cur-1]+x<=m) {
maxs(ans,cnt[cur-1]+y);return ;
}
maxs(ans,y);
dwn(i,cur-1,1){
if(x+sum[i]-sum[i-1]<=m) dfs(i,x+sum[i]-sum[i-1],y+cnt[i]-cnt[i-1]);
}
}
int main(){
m=read(),n=read();int u,v;
rep(i,1,n) u=read(),v=read(),sum[i]=sum[i-1]+u,cnt[i]=cnt[i-1]+v;
dfs(n+1,0,0);
printf("%d\n",ans);
return 0;
}

bzoj1734:裸二分答案。。。

#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
using namespace std;
#define rep(i,s,t) for(int i=s;i<=t;i++)
#define dwn(i,s,t) for(int i=s;i>=t;i--)
#define clr(x,c) memset(x,c,sizeof(x))
int read(){
int x=0;char c=getchar();
while(!isdigit(c)) c=getchar();
while(isdigit(c)) x=x*10+c-'0',c=getchar();
return x;
}
const int nmax=1e5+5;
int a[nmax],n,c;
bool check(int x){
int sum=1,pre=a[1];
rep(i,2,n) {
if(a[i]-pre>=x) sum++,pre=a[i];
}
return sum>=c;
}
int main(){
n=read(),c=read();
rep(i,1,n) a[i]=read();
sort(a+1,a+n+1);
int l=0,r=a[n],mid,ans=0;
while(l<=r){
mid=(l+r)>>1;
if(check(mid)) ans=mid,l=mid+1;
else r=mid-1;
}
printf("%d\n",ans);
return 0;
}

bzoj1733:二分答案+最大流就可以了。

#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
using namespace std;
#define rep(i,s,t) for(int i=s;i<=t;i++)
#define dwn(i,s,t) for(int i=s;i>=t;i--)
#define clr(x,c) memset(x,c,sizeof(x))
#define qwq(x) for(edge *o=head[x];o;o=o->next)
int read(){
int x=0;char c=getchar();
while(!isdigit(c)) c=getchar();
while(isdigit(c)) x=x*10+c-'0',c=getchar();
return x;
}
const int nmax=205;
const int maxn=160005;
const int inf=0x7f7f7f7f;
struct edge{
int to,cap,dist,p;edge *next,*rev;
};
edge es[maxn],*pt=es,*head[nmax],*p[nmax],*cur[nmax];
void add(int u,int v,int d){
pt->to=v;pt->dist=d;pt->cap=pt->p=1;pt->next=head[u];head[u]=pt++;
pt->to=u;pt->dist=d;pt->cap=pt->p=0;pt->next=head[v];head[v]=pt++;
head[u]->rev=head[v];head[v]->rev=head[u];
} int n,m,T,cnt[nmax],h[nmax];
void mins(int &a,int b){
if(a>b) a=b;
}
int maxflow(){
clr(cnt,0),cnt[0]=n;clr(h,0);
int flow=0,a=inf,x=1;edge *e;
while(h[1]<n){
for(e=cur[x];e;e=e->next) if(e->cap>0&&h[e->to]==h[x]-1) break;
if(e){
mins(a,e->cap),p[e->to]=cur[x]=e;x=e->to;
if(x==n){
while(x!=1) p[x]->cap-=a,p[x]->rev->cap+=a,x=p[x]->rev->to;
flow+=a,a=inf;
}
}else{
if(!--cnt[h[x]]) break;
h[x]=n;
for(e=head[x];e;e=e->next) if(e->cap>0&&h[x]>h[e->to]+1) h[x]=h[e->to]+1,cur[x]=e;
cnt[h[x]]++;
if(x!=1) x=p[x]->rev->to;
}
}
return flow;
}
bool check(int x){
rep(i,1,n) qwq(i) {
if(o->dist<=x) o->cap=o->p;
else o->cap=0;
}
return maxflow()>=T;
}
void maxs(int &a,int b){
if(a<b) a=b;
}
int main(){
n=read(),m=read(),T=read();int u,v,d,l=0,r=0;
rep(i,1,m) u=read(),v=read(),d=read(),add(u,v,d),add(v,u,d),maxs(r,d);
int ans=0,mid;
while(l<=r){
mid=(l+r)>>1;
if(check(mid)) ans=mid,r=mid-1;
else l=mid+1;
}
printf("%d\n",ans);
return 0;
}

bzoj1731:差分约束。s[j]-s[i]<=k/s[j]-s[i]>=k=>s[i]-s[j]<=-k/s[i]-s[i-1]>=0=>s[i-1]-s[i]<=0

#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
#include<queue>
using namespace std;
#define rep(i,s,t) for(int i=s;i<=t;i++)
#define dwn(i,s,t) for(int i=s;i>=t;i--)
#define clr(x,c) memset(x,c,sizeof(x))
#define qwq(x) for(edge *o=head[x];o;o=o->next)
#define ll long long
int read(){
int x=0;char c=getchar();
while(!isdigit(c)) c=getchar();
while(isdigit(c)) x=x*10+c-'0',c=getchar();
return x;
}
const int nmax=1005;
const int maxn=30005;
const ll inf=1e15;
struct edge{
int to,dist;edge *next;
};
edge es[maxn],*pt=es,*head[nmax];
void add(int u,int v,int d){
pt->to=v;pt->dist=d;pt->next=head[u];head[u]=pt++;
}
queue<int>q;
ll dist[nmax];int cnt[nmax];bool inq[nmax];
bool spfa(int n){
rep(i,2,n) dist[i]=inf;dist[1]=0;
clr(inq,0),clr(cnt,0);inq[1]=1,cnt[1]=1;
q.push(1);
while(!q.empty()){
int x=q.front();q.pop();inq[x]=0;
qwq(x) if(dist[o->to]>dist[x]+o->dist){
dist[o->to]=dist[x]+o->dist;
if(!inq[o->to]){
if(++cnt[o->to]==n) return false;
q.push(o->to);inq[o->to]=1;
}
}
}
}
int main(){
int n=read(),ml=read(),md=read(),u,v,d;
rep(i,1,ml) u=read(),v=read(),d=read(),add(u,v,d);
rep(i,1,md) u=read(),v=read(),d=read(),add(v,u,-d);
rep(i,2,n) add(i,i-1,0);
if(spfa(n)) {
if(dist[n]==inf) printf("-2\n");
else printf("%lld\n",dist[n]);
}else printf("-1\n");
return 0;
}

bzoj1726:求第二短路。我的写法不知道为什么WA了。。网上的题解也没人和我写的一样。。。

my code:

#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
#include<queue>
using namespace std;
#define rep(i,s,t) for(int i=s;i<=t;i++)
#define dwn(i,s,t) for(int i=s;i>=t;i--)
#define clr(x,c) memset(x,c,sizeof(x))
#define qwq(x) for(edge *o=head[x];o;o=o->next)
int read(){
int x=0;char c=getchar();
while(!isdigit(c)) c=getchar();
while(isdigit(c)) x=x*10+c-'0',c=getchar();
return x;
}
const int nmax=5005;
const int maxn=2000005;
const int inf=0x7f7f7f7f;
struct edge{
int to,dist;edge *next;
};
edge es[maxn],*pt=es,*head[nmax];
void add(int u,int v,int d){
pt->to=v;pt->dist=d;pt->next=head[u];head[u]=pt++;
pt->to=u;pt->dist=d;pt->next=head[v];head[v]=pt++;
} struct node{
int x,dist;
node(int x,int dist):x(x),dist(dist){};
node(){};
bool operator<(const node&rhs)const{
return dist>rhs.dist;}
};
priority_queue<node>q;
int da[nmax],db[nmax];
void dijkstra(){
clr(da,0x7f);clr(db,0x7f);da[1]=0;db[1]=0;q.push(node(1,0));
int tx,td;
while(!q.empty()){
node oo=q.top();q.pop();
tx=oo.x,td=oo.dist;
if(td!=da[tx]&&td!=db[tx]) continue;
qwq(tx) {
if(da[o->to]>td+o->dist){
db[o->to]=da[o->to];
da[o->to]=td+o->dist;
q.push(node(o->to,da[o->to]));
}else if(db[o->to]>td+o->dist){
db[o->to]=td+o->dist;
q.push(node(o->to,db[o->to]));
}
}
}
}
int main(){
int n=read(),m=read(),u,v,d;
rep(i,1,m) u=read(),v=read(),d=read(),add(u,v,d);
dijkstra();
printf("%d\n",db[n]);
return 0;
}

ac code:

#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
#include<queue>
using namespace std;
#define rep(i,s,t) for(int i=s;i<=t;i++)
#define dwn(i,s,t) for(int i=s;i>=t;i--)
#define clr(x,c) memset(x,c,sizeof(x))
#define qwq(x) for(edge *o=head[x];o;o=o->next)
int read(){
int x=0;char c=getchar();
while(!isdigit(c)) c=getchar();
while(isdigit(c)) x=x*10+c-'0',c=getchar();
return x;
}
const int nmax=5005;
const int maxn=2000005;
const int inf=0x7f7f7f7f;
struct edge{
int to,dist;edge *next;
};
edge es[maxn],*pt=es,*head[nmax];
void add(int u,int v,int d){
pt->to=v;pt->dist=d;pt->next=head[u];head[u]=pt++;
pt->to=u;pt->dist=d;pt->next=head[v];head[v]=pt++;
} struct node{
int x,dist;
node(int x,int dist):x(x),dist(dist){};
node(){};
bool operator<(const node&rhs)const{
return dist>rhs.dist;}
};
priority_queue<node>q;
int da[nmax],db[nmax];
void dijkstra(){
clr(da,0x7f);da[1]=0;q.push(node(1,0));
int tx,td;
while(!q.empty()){
node oo=q.top();q.pop();
tx=oo.x;td=oo.dist;
if(da[tx]!=td) continue;
qwq(tx) if(da[o->to]>td+o->dist){
da[o->to]=td+o->dist;
q.push(node(o->to,da[o->to]));
}
}
}
void DIJKSTRA(int n){
clr(db,0x7f);db[n]=0;q.push(node(n,0));
int tx,td;
while(!q.empty()){
node oo=q.top();q.pop();
tx=oo.x;td=oo.dist;
if(db[tx]!=td) continue;
qwq(tx) if(db[o->to]>td+o->dist){
db[o->to]=td+o->dist;
q.push(node(o->to,db[o->to]));
}
}
}
void mins(int &a,int b){
if(a>b) a=b;
}
int main(){
int n=read(),m=read(),u,v,d;
rep(i,1,m) u=read(),v=read(),d=read(),add(u,v,d);
dijkstra();DIJKSTRA(n);
int ans=da[n],res=inf,tmp;
rep(i,1,n) qwq(i){
tmp=da[i]+db[o->to]+o->dist;
if(tmp!=ans&&tmp<res) res=tmp;
}
rep(i,1,n) qwq(i) mins(res,da[i]+db[i]+o->dist*2);
printf("%d\n",res);
return 0;
}

bzoj1725:嘛状压dp。。居然忘了mod居然忘了mod居然忘了mod!!!

#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
using namespace std;
#define rep(i,s,t) for(int i=s;i<=t;i++)
#define clr(x,c) memset(x,c,sizeof(x))
const int mod=100000000;
int sta[10005],a[15],dp[15][10005];
int main(){
int n,m,u,v,d,cnt=0;scanf("%d%d",&n,&m);
rep(i,0,(1<<m)-1) if(!(i&(i<<1))) sta[++cnt]=i;
rep(i,1,n) rep(j,1,m){
scanf("%d",&u);
a[i]+=(1-u)*(1<<(j-1));
}
rep(i,1,cnt) if(!(a[1]&sta[i])) dp[1][i]=1;
rep(i,2,n) rep(j,1,cnt) if(!(a[i]&sta[j])){
rep(k,1,cnt) if(!(sta[j]&sta[k])) dp[i][j]=(dp[i][j]+dp[i-1][k])%mod;
}
int ans=0;
rep(i,1,cnt) ans=(ans+dp[n][i])%mod;
printf("%d\n",ans);
return 0;
}

bzoj1718:点双联通分量缩点后叶子节点个数/2就可以了。即是加最少的边让整个图双联通。将tarjan稍微修改一下就可以了。

#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
#include<stack>
using namespace std;
#define rep(i,s,t) for(int i=s;i<=t;i++)
#define dwn(i,s,t) for(int i=s;i>=t;i--)
#define clr(x,c) memset(x,c,sizeof(x))
#define qwq(x) for(edge *o=head[x];o;o=o->next)
int read(){
int x=0;char c=getchar();
while(!isdigit(c)) c=getchar();
while(isdigit(c)) x=x*10+c-'0',c=getchar();
return x;
}
const int nmax=5005;
const int maxn=20005;
const int inf=0x7f7f7f7f;
struct edge{
int to,op;edge *next;
};
edge es[maxn],*pt=es,*head[nmax];
void add(int u,int v,int cnt){
pt->to=v,pt->op=cnt,pt->next=head[u],head[u]=pt++;
pt->to=u,pt->op=cnt,pt->next=head[v],head[v]=pt++;
}
int pre[nmax],dfs_clock=0,scc_cnt=0,sccno[nmax],in[nmax];bool vis[maxn];
stack<int>s;
void mins(int &a,int b){
if(a>b) a=b;
}
int dfs(int x){
int lowu=pre[x]=++dfs_clock;s.push(x);
qwq(x) {
if(vis[o->op]) continue;
if(!pre[o->to]) vis[o->op]=1,mins(lowu,dfs(o->to));
else if(!sccno[o->to]) mins(lowu,pre[o->to]);
}
if(lowu==pre[x]){
scc_cnt++;int tx;
while(1){
tx=s.top();s.pop();
sccno[tx]=scc_cnt;
if(x==tx) break;
}
}
return lowu;
}
int main(){
int n=read(),m=read(),u,v;
rep(i,1,m) u=read(),v=read(),add(u,v,i);
dfs(1);
rep(i,1,n) qwq(i) if(sccno[i]!=sccno[o->to]) in[sccno[o->to]]++;
int ans=0;
rep(i,1,scc_cnt) if(in[i]==1) ans++;
printf("%d\n",(ans+1)>>1);
return 0;
}

bzoj1715:spfa判负圈就可以了,用dfs写会快。挖坑。。。没看清有向边无向边WA了。

#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
#include<queue>
using namespace std;
#define rep(i,s,t) for(int i=s;i<=t;i++)
#define dwn(i,s,t) for(int i=s;i>=t;i--)
#define clr(x,c) memset(x,c,sizeof(x))
#define qwq(x) for(edge *o=head[x];o;o=o->next)
int read(){
int x=0;char c=getchar();
while(!isdigit(c)) c=getchar();
while(isdigit(c)) x=x*10+c-'0',c=getchar();
return x;
}
const int nmax=505;
const int maxn=10005;
const int inf=0x7f7f7f7f;
struct edge{
int to,dist;edge *next;
};
edge es[maxn],*pt=es,*head[nmax];
void add(int u,int v,int d){
pt->to=v,pt->dist=d,pt->next=head[u],head[u]=pt++;
}
int dist[nmax],cnt[nmax];bool inq[nmax];
queue<int>q;
bool spfa(int n){
clr(dist,0x7f);dist[1]=0;
clr(inq,0);inq[1]=1;
clr(cnt,0);cnt[1]=1;
while(!q.empty()) q.pop();q.push(1);
int tx;
while(!q.empty()){
tx=q.front();q.pop();inq[tx]=0;
qwq(tx) if(dist[o->to]>dist[tx]+o->dist){
dist[o->to]=dist[tx]+o->dist;
if(!inq[o->to]) {
if(++cnt[o->to]==n) return true;
inq[o->to]=1;q.push(o->to);
}
}
}
return false;
}
int main(){
int F=read();
while(F--){
clr(head,0);pt=es;
int n=read(),m=read(),w=read(),u,v,d;
rep(i,1,m) u=read(),v=read(),d=read(),add(u,v,d),add(v,u,d);
rep(i,1,w) u=read(),v=read(),d=read(),add(u,v,-d);
if(spfa(n)) printf("YES\n");
else printf("NO\n");
}
return 0;
}

bzoj1710:区间dp。

#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
using namespace std;
#define rep(i,s,t) for(int i=s;i<=t;i++)
#define dwn(i,s,t) for(int i=s;i>=t;i--)
#define clr(x,c) memset(x,c,sizeof(x))
int read(){
int x=0;char c=getchar();
while(!isdigit(c)) c=getchar();
while(isdigit(c)) x=x*10+c-'0',c=getchar();
return x;
}
const int nmax=2005;
char s[nmax];
int a[nmax],w[30],dp[nmax][nmax];
int main(){
int m=read(),n=read();scanf("%s",s+1);
rep(i,1,n) a[i]=s[i]-'a';
rep(i,1,m){
scanf("%s",s);
w[s[0]-'a']=min(read(),read());
}
int k;
rep(i,1,n-1) {
rep(j,1,n-i){
k=i+j;
dp[j][k]=min(dp[j][k-1]+w[a[k]],dp[j+1][k]+w[a[j]]);
if(a[j]==a[k]) dp[j][k]=min(dp[j][k],dp[j+1][k-1]);
}
}
printf("%d\n",dp[1][n]);
return 0;
}

bzoj1709:暴力枚举

#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
using namespace std;
#define rep(i,s,t) for(int i=s;i<=t;i++)
#define dwn(i,s,t) for(int i=s;i>=t;i--)
#define clr(x,c) memset(x,c,sizeof(x))
int read(){
int x=0;char c=getchar();
while(!isdigit(c)) c=getchar();
while(isdigit(c)) x=x*10+c-'0',c=getchar();
return x;
}
const int nmax=105;
int a[nmax][nmax],dp[nmax][nmax];
int xx[9]={0,0,0,1,1,1,-1,-1,-1};
int yy[9]={0,1,-1,1,0,-1,1,0,-1};
int main(){
int n=read(),K=read(),u,v,tx,ty;
rep(i,1,K) u=read(),v=read(),a[u][v]++;
rep(i,1,n) rep(j,1,n) if(a[i][j]){
rep(k,1,8) rep(t,1,n){
tx=i+xx[k]*t,ty=j+yy[k]*t;
if(tx<1||ty<1||tx>n||ty>n) break;
dp[tx][ty]+=a[i][j];
}
dp[i][j]+=a[i][j];
}
int ans=0;
rep(i,1,n) rep(j,1,n) if(dp[i][j]==K) ans++;
printf("%d\n",ans);
return 0;
}

bzoj1708:。。。背包dp。。。

#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
using namespace std;
#define rep(i,s,t) for(int i=s;i<=t;i++)
#define dwn(i,s,t) for(int i=s;i>=t;i--)
#define clr(x,c) memset(x,c,sizeof(x))
#define ll long long
ll read(){
ll x=0;char c=getchar();
while(!isdigit(c)) c=getchar();
while(isdigit(c)) x=x*10+c-'0',c=getchar();
return x;
}
ll a[30],dp[10005];
int main(){
int n=read(),m=read();
rep(i,1,n) a[i]=read();
dp[0]=1;
rep(i,1,n) rep(j,a[i],m) dp[j]+=dp[j-a[i]];
printf("%lld\n",dp[m]);
return 0;
}

bzoj1707:贪心。将右端点排序后,取适合的最小spf。因为这样子取对后面的影响肯定最小!。有更优但复杂写法挖坑!。。。

#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
using namespace std;
#define rep(i,s,t) for(int i=s;i<=t;i++)
int read(){
int x=0;char c=getchar();
while(!isdigit(c)) c=getchar();
while(isdigit(c)) x=x*10+c-'0',c=getchar();
return x;
}
const int nmax=2505;
struct edge{
int l,r;
bool operator<(const edge&rhs)const{
return r<rhs.r;}
};
edge es[nmax];
struct node{
int spf,num;
bool operator<(const node&rhs)const{
return spf<rhs.spf;}
};
node ns[nmax];
int main(){
int n=read(),m=read();
rep(i,1,n) es[i].l=read(),es[i].r=read();
rep(i,1,m) ns[i].spf=read(),ns[i].num=read();
sort(es+1,es+n+1);sort(ns+1,ns+m+1);
int ans=0;
rep(i,1,n){
rep(j,1,m) {
if(ns[j].spf>es[i].r) break;
if(ns[j].spf>=es[i].l&&ns[j].num) {
ns[j].num--;ans++;break;
}
}
}
printf("%d\n",ans);
return 0;
}

bzoj1598:A*启发式搜索+最短路求k短路

//#3哇咔咔好开心。。。
#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
#include<queue>
using namespace std;
#define rep(i,s,t) for(int i=s;i<=t;i++)
#define dwn(i,s,t) for(int i=s;i>=t;i--)
#define clr(x,c) memset(x,c,sizeof(x))
#define qwq(x) for(edge *o=head[x];o;o=o->next)
#define qaq(x) for(edge *o=h[x];o;o=o->next)
int read(){
int x=0;char c=getchar();
while(!isdigit(c)) c=getchar();
while(isdigit(c)) x=x*10+c-'0',c=getchar();
return x;
}
const int nmax=1005;
const int maxn=20005;
const int inf=0x7f7f7f7f;
struct edge{
int to,dist;edge *next;
};
edge es[maxn],*pt=es,*head[nmax],*h[nmax];
void add(int u,int v,int d){
pt->to=v,pt->dist=d,pt->next=head[u],head[u]=pt++;
pt->to=u,pt->dist=d,pt->next=h[v],h[v]=pt++;
}
struct node{
int x,dist;
node(int x,int dist):x(x),dist(dist){};
node(){};
bool operator<(const node&rhs)const{
return dist>rhs.dist;}
};
priority_queue<node>q;
int dist[nmax],tm[nmax],ans[105],n,m,K;
void dijkstra(){
clr(dist,0x7f);dist[1]=0;q.push(node(1,0));
node oo;int tx,td;
while(!q.empty()){
oo=q.top();q.pop();
tx=oo.x,td=oo.dist;
if(dist[tx]!=td) continue;
qaq(tx) if(dist[o->to]>td+o->dist){
dist[o->to]=td+o->dist;
q.push(node(o->to,dist[o->to]));
}
}
}
void AX(){
clr(ans,-1);
if(dist[n]==inf) return ;
q.push(node(n,dist[n]));node oo;int tx,td,temp;
while(!q.empty()){
oo=q.top();q.pop();
tx=oo.x,td=oo.dist;temp=++tm[tx];
if(tx==1) {
ans[temp]=td;
if(temp==K) break;
}
if(temp<=K) qwq(tx) q.push(node(o->to,td-dist[tx]+dist[o->to]+o->dist));
}
}
int main(){
n=read(),m=read(),K=read();int u,v,d;
rep(i,1,m) u=read(),v=read(),d=read(),add(u,v,d);
dijkstra();AX();
rep(i,1,K) printf("%d\n",ans[i]);
return 0;
}

bzoj1706:离散化+矩阵快速幂 。yyl用map判重而且没用struct写矩阵乘法快了很多。不过关键是map吧。挖坑!我不会用map。。。 而且变量名短+清晰、像这里o.from,o.to,o.dist好丑啊、、、

#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
using namespace std;
#define rep(i,s,t) for(int i=s;i<=t;i++)
#define dwn(i,s,t) for(int i=s;i>=t;i--)
#define clr(x,c) memset(x,c,sizeof(x))
int read(){
int x=0;char c=getchar();
while(!isdigit(c)) c=getchar();
while(isdigit(c)) x=x*10+c-'0',c=getchar();
return x;
}
const int nmax=205;
const int inf=0x3f3f3f3f;
struct edge{
int from,to,dist;
};
edge es[nmax];
int ns[nmax],cnt=0;
void mins(int &a,int b){
if(a>b) a=b;
}
struct mtx{
int a[205][205];
mtx(){
clr(a,0x3f);
}
mtx operator*(const mtx&o)const{
mtx tmp;
rep(i,1,cnt) rep(j,1,cnt) rep(k,1,cnt) mins(tmp.a[i][j],a[i][k]+o.a[k][j]);
return tmp;
}
}a,b;
int main(){
int n=read(),m=read(),s=read(),t=read(),u,v,d;
rep(i,1,m) {
edge &o=es[i];o.dist=read(),o.from=read(),o.to=read();
ns[++cnt]=o.from,ns[++cnt]=o.to;
}
sort(ns+1,ns+cnt+1);
cnt=unique(ns+1,ns+cnt+1)-ns-1; rep(i,1,m) {
edge &o=es[i];
o.from=lower_bound(ns+1,ns+cnt+1,o.from)-ns;
o.to=lower_bound(ns+1,ns+cnt+1,o.to)-ns;
b.a[o.from][o.to]=b.a[o.to][o.from]=o.dist;
} n--;a=b;
while(n){
if(n&1) a=a*b;
n>>=1;b=b*b;
}
s=lower_bound(ns+1,ns+cnt+1,s)-ns;
t=lower_bound(ns+1,ns+cnt+1,t)-ns;
printf("%d\n",a.a[s][t]);
return 0;
}

8.20 usaco的更多相关文章

  1. USACO翻译:USACO 2012 FEB Silver三题

    USACO 2012 FEB SILVER 一.题目概览 中文题目名称 矩形草地 奶牛IDs 搬家 英文题目名称 planting cowids relocate 可执行文件名 planting co ...

  2. USACO翻译:USACO 2012 JAN三题(2)

    USACO 2012 JAN(题目二) 一.题目概览 中文题目名称 叠干草 分干草 奶牛联盟 英文题目名称 stacking baleshare cowrun 可执行文件名 stacking bale ...

  3. USACO翻译:USACO 2012 JAN三题(1)

    USACO 2012 JAN(题目一) 一.题目概览 中文题目名称 礼物 配送路线 游戏组合技 英文题目名称 gifts delivery combos 可执行文件名 gifts delivery c ...

  4. USACO翻译:USACO 2014 JAN三题(2)

    USACO 2014 JAN 一.题目概览 中文题目名称 队伍平衡 滑雪录像 滑雪场建设 英文题目名称 bteams recording skicourse 可执行文件名 bteams recordi ...

  5. USACO翻译:USACO 2014 JAN三题(1)

    USACO 2014 JAN 一.题目概览 中文题目名称 滑雪场设计 滑雪降速 滑雪场评级 英文题目名称 skidesign slowdown skilevel 可执行文件名 skidesign sl ...

  6. USACO翻译:USACO 2014 MARCH Silver三题

    USACO 2014 MARCH 一.题目概览 中文题目名称 农田灌溉 懒牛 牛叫 英文题目名称 irrigation lazy mooomoo 可执行文件名 irrigation lazy mooo ...

  7. [题解]USACO 1.3 Ski Course Design

    Ski Course Design Farmer John has N hills on his farm (1 <= N <= 1,000), each with an integer ...

  8. 【COGS】714. USACO 1.3.2混合牛奶(贪心+水题)

    http://cojs.tk/cogs/problem/problem.php?pid=714 在hzwer的刷题记录上,默默地先跳过2题T_T...求凸包和期望的..T_T那是个啥..得好好学习 看 ...

  9. usaco 2010年3月银组题解

    usaco银组解题报告 一.石子游戏如果把‘O’当作0,‘X’当做1,则N个洞的每一种状态都可以看做是一个N位二进制数.于是,这个问题就变成了求环绕的N位格雷码.幸运的是,这个结构很容易就能够用一个简 ...

随机推荐

  1. 关于hadoop2.4.2版本学习时遇到的问题

    问题一:namenode启动失败 描述:在初始化后hadoop后,发现datanode启动失败,namenode则可以正常启动,如果把用户换成root权限,再次启动时,则namenode和datano ...

  2. c#中sqlhelper类的编写(一)

    在.net平台的项目开发中,凡是用到数据库交互的,都有必要了解SqlHelper类的原理. 步骤一: 我就拿WPF项目开发作为例子.首先要新建一个App.config(应用程序配置文件).注意,在VS ...

  3. android.support.v4.widget.DrawerLayout使用

    activity_main.xml布局如下: <android.support.v4.widget.DrawerLayout xmlns:android="http://schemas ...

  4. shell echo打印换行的方法

    echo要支持同C语言一样的\转义功能,只需要加上参数-e,如下所示: [~]#echo "Hello world.\nHello sea" Hello world.\nHello ...

  5. 【BZOJ 1934】 [Shoi2007]Vote 善意的投票

    Description 幼儿园里有n个小朋友打算通过投票来决定睡不睡午觉.对他们来说,这个问题并不是很重要,于是他们决定发扬谦让精神.虽然每个人都有自己的主见,但是为了照顾一下自己朋友的想法,他们也可 ...

  6. 【BZOJ 1066】[SCOI2007]蜥蜴

    Description 在一个r行c列的网格地图中有一些高度不同的石柱,一些石柱上站着一些蜥蜴,你的任务是让尽量多的蜥蜴逃到边界外. 每行每列中相邻石柱的距离为1,蜥蜴的跳跃距离是d,即蜥蜴可以跳到平 ...

  7. 【BZOJ1030】文本生成器

    Description JSOI交给队员ZYX一个任务,编制一个称之为“文本生成器”的电脑软件:该软件的使用者是一些低幼人群,他们现在使用的是GW文本生成器v6版.该软件可以随机生成一些文章―――总是 ...

  8. WdatePicker 设置开始时间和结束时间

    开始时间: <input type="text" placeholder=" -请选择- " readonly="readonly" ...

  9. 3D游戏常用技巧Normal Mapping (法线贴图)原理解析——高级篇

    1.概述 上一篇博客,3D游戏常用技巧Normal Mapping (法线贴图)原理解析——基础篇,讲了法线贴图的基本概念和使用方法.而法线贴图和一般的纹理贴图一样,都需要进行压缩,也需要生成mipm ...

  10. 如何安装Favicon

    如何安装Favicon favicon.ico图像放在根目录下(也可以是其他目录)在页面源文件的<head></head>标签之间插入 <link rel="s ...