zoukankan      html  css  js  c++  java
  • USACO 刷题记录bzoj

    bzoj 1606: [Usaco2008 Dec]Hay For Sale 购买干草——背包

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int h,n,f[50007],k;
    int main()
    {
        h=read(); n=read();
        f[0]=1;
        for(int i=1;i<=n;i++){
            k=read();
            for(int j=h;j>=k;j--) if(f[j-k]) f[j]=1;
        }
        for(int i=h;i>=0;i--)if(f[i]){printf("%d
    ",i); break;}
        return 0;
    }
    View Code

     bzoj 1607: [Usaco2008 Dec]Patting Heads 轻拍牛头——筛数

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,f[1000007],v[100007],ans[1000007];
    int main()
    {
        n=read();
        for(int i=1;i<=n;i++) v[i]=read(),f[v[i]]++;
        for(int i=1;i<=(int)1e6;i++)if(f[i]){
            for(int j=i;j<=(int)1e6;j+=i) if(f[j]) ans[j]+=f[i];
        }
        for(int i=1;i<=n;i++) printf("%d
    ",ans[v[i]]-1);
        return 0;
    }
    View Code

     bzoj 1597: [Usaco2008 Mar]土地购买——斜率优化dp

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #define LL long long
    using namespace std;
    const int M=50007;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    LL x[M],y[M],f[M];
    int q[M],n,tot;
    struct node{LL x,y;}a[M];
    bool cmp(node a,node b){return a.x!=b.x?a.x<b.x:a.y<b.y;}
    double slop(int a,int b){return (double)(f[b]-f[a])/(y[a+1]-y[b+1]);}
    int main()
    {
        n=read();
        for(int i=1;i<=n;i++) a[i].x=read(),a[i].y=read();
        sort(a+1,a+1+n,cmp);
        for(int i=1;i<=n;i++){
            while(tot&&y[tot]<=a[i].y) tot--;
            x[++tot]=a[i].x; y[tot]=a[i].y;
        }
        int head=0,tail=0;
        for(int i=1;i<=tot;i++){
            while(head<tail&&slop(q[head],q[head+1])<x[i]) head++;
            int v=q[head];
            f[i]=f[v]+y[v+1]*x[i];
            while(head<tail&&slop(q[tail-1],q[tail])>slop(q[tail],i)) tail--;
            q[++tail]=i;
        }
        printf("%lld
    ",f[tot]);
        return 0;
    }
    View Code

     bzoj 1699: [Usaco2007 Jan]Balanced Lineup排队 ——zkw版

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    const int N=1<<19,inf=0x3f3f3f3f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,q,l,r;
    int mx[N<<1],mn[N<<1];
    int push_ans(int l,int r){
        int mx1=0,mn1=inf;
        for(l+=N-1,r+=N+1;r-l!=1;l>>=1,r>>=1){
            if(~l&1) mx1=max(mx1,mx[l^1]),mn1=min(mn1,mn[l^1]);
            if(r&1)     mx1=max(mx1,mx[r^1]),mn1=min(mn1,mn[r^1]);
        }
        return mx1-mn1;
    }
    int main()
    {
        n=read(); q=read();
        for(int i=1;i<=n;i++) mx[N+i]=mn[N+i]=read();
        for(int i=N-1;i;i--) mx[i]=max(mx[i<<1],mx[i<<1^1]),mn[i]=min(mn[i<<1],mn[i<<1^1]);
        for(int i=1;i<=q;i++){
            l=read(); r=read();
            printf("%d
    ",push_ans(l,r));
        }
        return 0;
    }
    View Code

     bzoj 1602: [Usaco2008 Oct]牧场行走——lca

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    const int M=1e3+7;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int vis[M],d[M],q[M];
    int n,k,first[M],cnt;
    struct node{int to,w,next;}e[2*M];
    void ins(int a,int b,int w){e[++cnt]=(node){b,w,first[a]}; first[a]=cnt;}
    void insert(int a,int b,int w){ins(a,b,w); ins(b,a,w);}
    void push_ans(int k){
        int head=0,tail=1;
        q[0]=k; vis[k]=1;
        while(head!=tail){
            int x=q[head++];
            for(int i=first[x];i;i=e[i].next){
                int now=e[i].to;
                if(!vis[now]){
                    vis[now]=1;
                    d[now]=d[x]+e[i].w;
                    q[tail++]=now;
                }
            }
        }
    }
    int main()
    {
        int x,y,w;
        n=read(); k=read();
        for(int i=1;i<n;i++) x=read(),y=read(),w=read(),insert(x,y,w);
        for(int i=1;i<=k;i++){
            x=read(); y=read();
            memset(vis,0,sizeof(vis));
            memset(d,0,sizeof(d));
            push_ans(x);
            printf("%d
    ",d[y]);
        }
        return 0;
    }
    View Code

     bzoj 1610: [Usaco2008 Feb]Line连线游戏——几何

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<cmath>
    using namespace std;
    const int M=257;
    bool pd(double x,double y){return fabs(x-y)<1e-7;}
    int n,cnt,ans;
    double x[M],y[M],a[M*M];
    bool cmp(double x,double y){return x<y;}
    int main()
    {
        scanf("%d",&n);
        for(int i=1;i<=n;i++) scanf("%lf %lf",&x[i],&y[i]);
        for(int i=1;i<=n;i++)
            for(int j=i+1;j<=n;j++){
                if(!pd(x[i],x[j])) a[++cnt]=(y[i]-y[j])/(x[i]-x[j]);
                else ans=1;
            }
        sort(a+1,a+1+cnt,cmp);
        if(cnt>=1) ans++;
        for(int i=2;i<=cnt;i++) if(!pd(a[i],a[i-1])) ans++;
        printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj 1609: [Usaco2008 Feb]Eating Together麻烦的聚餐 ——dp

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    const int M=350007,inf=0x3f3f3f3f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,c[M],f[M][4],ans=inf;
    int main()
    {
        n=read();
        for(int i=1;i<=n;i++) c[i]=read();
        memset(f,0x3f,sizeof(f));
        f[0][1]=f[0][2]=f[0][3]=0;
        for(int k=1;k<=n;k++)
            for(int i=1;i<=3;i++){
                for(int j=1;j<=i;j++) f[k][i]=min(f[k][i],f[k-1][j]);
                if(i!=c[k]) f[k][i]++;
            }
        for(int i=1;i<=3;i++) ans=min(ans,f[n][i]);
        memset(f,0x3f,sizeof(f));
        f[n+1][1]=f[n+1][2]=f[n+1][3]=0;
        for(int k=n;k>=1;k--)
            for(int i=1;i<=3;i++){
                for(int j=1;j<=i;j++) f[k][i]=min(f[k][i],f[k+1][j]);
                if(i!=c[k]) f[k][i]++;
            }
        for(int i=1;i<=3;i++) ans=min(ans,f[1][i]);
        printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj 1625: [Usaco2007 Dec]宝石手镯——01背包

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    const int M=3507,N=15007;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,c[M],w[M],f[N];
    int main()
    {
        n=read(); m=read();
        for(int i=1;i<=n;i++) c[i]=read(),w[i]=read();
        for(int i=1;i<=n;i++)
            for(int j=m;j>=c[i];j--) f[j]=max(f[j],f[j-c[i]]+w[i]);
        printf("%d
    ",f[m]);
        return 0;
    }
    View Code

     bzoj 1617: [Usaco2008 Mar]River Crossing渡河问题——简单dp

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<set>
    using namespace std;
    const int M=5507,inf=0x3f3f3f3f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,f[M],w[M],s[M];
    int main()
    {
        n=read(); s[0]=read();
        for(int i=1;i<=n;i++) w[i]=read();
        for(int i=1;i<=n;i++) s[i]=s[i-1]+w[i];
        for(int i=1;i<=n;i++){
            f[i]=inf;
            for(int j=1;j<=i;j++) f[i]=min(f[i],f[i-j]+s[j]+s[0]);
        }
        printf("%d
    ",f[n]-s[0]);
        return 0;
    }
    View Code

     bzoj  1650: [Usaco2006 Dec]River Hopscotch 跳石子——二分

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    const int M=55007;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int L,n,m,s[M];
    bool check(int mx){
        int cnt=0,sum=0;
        for(int i=1;i<=n;i++){
            if(s[i]-sum<=mx) cnt++;
            else sum=s[i];
        }
        return cnt<=m;
    }
    int main()
    {
        L=read(); n=read(); m=read();
        for(int i=1;i<=n;i++) s[i]=read();
        s[++n]=L;
        sort(s+1,s+1+n);
        int l=0,r=L+1;
        while(l<=r){
            int mid=(l+r)>>1;
            if(check(mid)) l=mid+1;
            else r=mid-1;
        }printf("%d
    ",l);
        return 0;
    }
    View Code

     bzoj 2718: [Violet 4]毕业旅行——二分图匹配+最大反链

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    using namespace std;
    const int M=557,inf=0x3f3f3f3f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int ans,n,m,S,T,f[M][M];
    int vis[M],d[M],first[M],cur[M],cnt=1;
    struct node{int to,next,flow;}e[M*M];
    void ins(int a,int b,int w){e[++cnt]=(node){b,first[a],w}; first[a]=cnt;};
    void insert(int a,int b){ins(a,b,1); ins(b,a,0);}
    void floyd(){
        for(int k=1;k<=n;k++)
         for(int i=1;i<=n;i++)
          for(int j=1;j<=n;j++)
           f[i][j]|=f[i][k]&f[k][j];
        for(int i=1;i<=n;i++) f[i][i]=0;
    }
    queue<int>q;
    int bfs(){
        memset(d,-1,sizeof(d));
        q.push(S); d[S]=0; 
        while(!q.empty()){
            int x=q.front(); q.pop(); 
            for(int i=first[x];i;i=e[i].next){
                int now=e[i].to;
                if(e[i].flow&&d[now]==-1) d[now]=d[x]+1,q.push(now);
            }
        }
        return d[T]!=-1;
    }
    int dfs(int x,int a){
        if(x==T||a==0) return a;
        int f,flow=0;
        for(int& i=cur[x];i;i=e[i].next){
            int now=e[i].to;
            if(e[i].flow&&d[now]==d[x]+1&&(f=dfs(now,min(a,e[i].flow)))>0){
                e[i].flow-=f; e[i^1].flow+=f;
                flow+=f;
                a-=f; if(!a) break;
            }
        }
        return flow;
    }
    int main()
    {
        int x,y;
        n=read(); m=read(); ans=n;
        S=0; T=2*n+1;
        for(int i=1;i<=m;i++) x=read(),y=read(),f[x][y]=1;
        floyd();
        for(int i=1;i<=n;i++)
         for(int j=1;j<=n;j++)
          if(f[i][j]) insert(i,j+n);
        for(int i=1;i<=n;i++) insert(S,i),insert(i+n,T);
        while(bfs()){
            for(int i=S;i<=T;i++) cur[i]=first[i];
            ans-=dfs(S,inf);
        }printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj 1613: [Usaco2007 Jan]Running贝茜的晨练计划——dp

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    const int M=1e4+7;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,w[M];
    int f[M][1007];
    int main()
    {
        n=read(); m=read();
        for(int i=1;i<=n;i++) w[i]=read();
        for(int i=1;i<=n;i++){
            for(int j=1;j<=m;j++) f[i][j]=f[i-1][j-1]+w[i];
            f[i][0]=f[i-1][0];
            for(int j=1;j<=m;j++) if(i>j) f[i][0]=max(f[i][0],f[i-j][j]);
        }
        printf("%d
    ",f[n][0]);
        return 0;
    }
    View Code

     bzoj 1230: [Usaco2008 Nov]lites 开关灯——线段树

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    const int M=1<<18;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m;
    int k,L,R;
    struct node{
        node *lc,*rc;
        int l,r,mid,sum,h,sz;
        void pr(){sum=sz-sum; h^=1;}
        void up(){sum=lc->sum+rc->sum;}
        void down(){h=0; lc->pr(); rc->pr();}
        void modify(){
            if(L<=l&&r<=R) return pr();
            if(h) down();
            if(L<=mid) lc->modify();
            if(R>mid) rc->modify();
            up();
        }
        int query(){
            if(L<=l&&r<=R) return sum;
            if(h) down();
            int tot=0;
            if(L<=mid) tot+=lc->query();
            if(R>mid)  tot+=rc->query();
            return tot;
        }
        node*build(int L,int R);
    }tr[M],*np=tr+1;
    node*node::build(int L,int R){
        l=L; r=R; sz=R-L+1;
        if(L<R){
            mid=(L+R)>>1;
            lc=++np;
            lc->build(L,mid);
            rc=++np;
            rc->build(mid+1,R);
        }
    }
    int main(){
        n=read(); m=read();
        tr[1].build(1,n);
        for(int i=1;i<=m;i++){
            k=read(); L=read(); R=read();
            if(!k) tr[1].modify();
            else if(k)  printf("%d
    ",tr[1].query());
        }
        return 0;
    }
    View Code

     bzoj1600 1600: [Usaco2008 Oct]建造栅栏——简单dp

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n;
    int f[15][2507];
    int main()
    {
        n=read();
        f[0][0]=1; 
        int mx=(n+1)/2-1;
        for(int k=1;k<=4;k++)
         for(int i=1;i<=n;i++)
          for(int j=1;j<=min(i,mx);j++)
              f[k][i]+=f[k-1][i-j];
        printf("%d
    ",f[4][n]);
        return 0;
    }
    View Code

     bzoj 1612: [Usaco2008 Jan]Cow Contest奶牛的比赛

    n^3算法 用的bitset可能快点n^3/32吧 暂时没有更优的方法

    #include<cstdio>
    #include<bitset>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m;
    bitset<107> f[107];
    int main(){
        int x,y;
        n=read(); m=read();
        for(int i=1;i<=m;i++) x=read(),y=read(),f[x][y]=1;
        for(int k=1;k<=n;++k)
            for(int i=1;i<=n;i++) if(f[i][k]) f[i]|=f[k];
        int res=0;
        for(int i=1;i<=n;++i){
            int sum=1;
            for(int j=1;j<=n;j++) sum+=f[i][j]|f[j][i];
            if(sum==n) ++res;
        }
        printf("%d",res);
        return 0;
    }
    View Code

     好的还有nm/32的写法 但是实测没快多少

    #include<cstdio>
    #include<bitset>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    #include<iostream>
    using namespace std;
    const int M=107;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,ans;
    bitset<107>f[107];
    int first[M],cnt,in[M],vis[M],map[M][M];
    queue<int>q;
    int main(){
        int x,y;
        n=read(); m=read();
        for(int i=1;i<=m;i++) x=read(),y=read(),map[y][x]=1,in[x]++;
        for(int i=1;i<=n;i++){
            f[i][i]=1;
            if(!in[i]) q.push(i),vis[i]=1;
        }
        while(!q.empty()){
            int x=q.front(); q.pop();
            for(int i=1;i<=n;i++)if(map[x][i]&&!vis[i]){
                in[i]--;
                f[i]|=f[x];
                if(!in[i]) vis[i]=1,q.push(i);
            }
        }
        int ans=0;
         for(int i=1;i<=n;i++){
            int sum=0;
            for(int j=1;j<=n;j++) sum+=f[i][j]|f[j][i];
            if(sum==n) ans++;
        }
        printf("%d
    ",ans);
        return 0;
    }
    View Code

    bzoj1614: [Usaco2007 Jan]Telephone Lines架设电话线——二分答案

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    using namespace std;
    const int M=2e4+7;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,k,mx;
    int first[M],cnt,d[M],vis[M];
    struct node{int to,next,w;}e[10*M];
    void ins(int a,int b,int w){e[++cnt]=(node){b,first[a],w}; first[a]=cnt;}
    void insert(int a,int b,int w){ins(a,b,w); ins(b,a,w);}
    queue<int>q;
    int spfa(int mx){
        memset(vis,0,sizeof(d));
        memset(d,0x3f,sizeof(d));
        q.push(1); d[1]=0;
        while(!q.empty()){
            int x=q.front(); q.pop();
            vis[x]=0;
            for(int i=first[x];i;i=e[i].next){
                int now=e[i].to,v=d[x]+(e[i].w>mx);
                if(d[now]>v){
                    d[now]=v;
                    if(!vis[now]) vis[now]=1,q.push(now);
                }
            }
        }
        return d[n]<=k;
    }
    int main()
    {
        int x,y,w;
        n=read(); m=read(); k=read();
        for(int i=1;i<=m;i++) x=read(),y=read(),w=read(),insert(x,y,w),mx=max(mx,w);
        int ans=-1,l=0,r=mx;
        while(l<=r){
            int mid=(l+r)>>1;
            if(spfa(mid)) ans=mid,r=mid-1;
            else l=mid+1;
        }printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj  1603. -- [Usaco2008 Oct]打谷机——简单模拟

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    using namespace std;
    const int M=1e3+7;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,cnt,d[M];
    struct node{int x,y,c;}e[M];
    bool cmp(node a,node b){return a.x<b.x;}
    int main()
    {
        n=read();
        for(int i=1;i<n;i++) e[i].x=read(),e[i].y=read(),e[i].c=read();
        sort(e+1,e+n,cmp);
        d[1]=0;
        for(int i=1;i<n;i++)
         if(e[i].c==0) d[e[i].y]=d[e[i].x];
         else d[e[i].y]=1-d[e[i].x];
        printf("%d
    ",d[n]);
        return 0;
    }
    View Code

     bzoj 1599: [Usaco2008 Oct]笨重的石子

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int s[4],mx,ans;
    int f[107],sum;
    int main()
    {
        for(int i=1;i<=3;i++) s[i]=read(),sum+=s[i];
        for(int s1=1;s1<=s[1];s1++)
         for(int s2=1;s2<=s[2];s2++)
          for(int s3=1;s3<=s[3];s3++)
           f[s1+s2+s3]++;
        for(int i=1;i<=sum;i++) if(f[i]>mx) mx=f[i],ans=i;
        printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj 1692: [Usaco2007 Dec]队列变换——后缀数组

     暂时不会写 留坑代填 填在后面了233(没用后缀数组QAQ)

    bzoj 1616: [Usaco2008 Mar]Cow Travelling游荡的奶牛——简单dp

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    const int M=107;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,T;
    int sx,sy,ex,ey;
    int f[M][M][25],map[M][M];
    int xi[5]={0,0,1,0,-1},yi[5]={0,1,0,-1,0};
    char s[155];
    int main()
    {
        n=read(); m=read(); T=read();
        for(int i=1;i<=n;i++){
            scanf("%s",s+1);
            for(int j=1;j<=m;j++) if(s[j]=='.') map[i][j]=1;
        }
        sx=read(); sy=read(); ex=read(); ey=read();
        f[sx][sy][0]=1;
        for(int k=1;k<=T;k++)
         for(int x=1;x<=n;x++)
          for(int y=1;y<=m;y++)if(map[x][y])
              for(int i=1;i<=4;i++){
                  int nx=x+xi[i],ny=y+yi[i];
                  if(nx<1||nx>n||ny<1||ny>m||!map[nx][ny]||!f[nx][ny][k-1]) continue;
                  f[x][y][k]+=f[nx][ny][k-1];
              }
        printf("%d
    ",f[ex][ey][T]);
        return 0;
    }
    View Code

     bzoj1666 : [Usaco2006 Oct]Another Cow Number Game 奶牛的数字游戏——模拟

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    const int M=107;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,ans;
    int main()
    {
        n=read();
        while(n!=1){
            ans++;
            if(n%2) n=n*3+1;
            else n/=2;
        }printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj 1626: [Usaco2007 Dec]Building Roads 修建道路——最小生成树

    1. Kruskal 这个写法超级慢QAQ 直接n^2logn^2 暴力

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<cmath>
    using namespace std;
    const int M=1e3+7;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,f[M],map[M][M];
    int find(int x){return f[x]==x?x:f[x]=find(f[x]);}
    double x[M],y[M],ans;
    double calc(int p,int q){return sqrt((x[p]-x[q])*(x[p]-x[q])+(y[p]-y[q])*(y[p]-y[q]));}
    int cnt,sum;
    struct node{int from,to; double d;}e[M*M];
    bool cmp(node a,node b){return (b.d-a.d)>1e-7;}
    int main()
    {
        int p,q;
        n=read(); m=read();
        for(int i=1;i<=n;i++) f[i]=i;
        for(int i=1;i<=n;i++) scanf("%lf %lf",&x[i],&y[i]);
        for(int i=1;i<=m;i++){
            p=read(); q=read();
            map[p][q]=map[q][p]=1;
            e[++cnt]=(node){p,q,calc(p,q)};
        }
        sort(e+1,e+1+cnt,cmp);
        for(int i=1;i<=cnt;i++){
            int p=find(e[i].from),q=find(e[i].to);
            if(p==q) continue;
            sum++; f[q]=p;
        }
        if(sum==n) return printf("%.2lf
    ",ans),0;
        cnt=0;
        for(int i=1;i<=n;i++)
            for(int j=i+1;j<=n;j++)if(!map[i][j])
                e[++cnt]=(node){i,j,calc(i,j)};
        sort(e+1,e+1+cnt,cmp);
        for(int i=1;i<=cnt;i++){
            int p=find(e[i].from),q=find(e[i].to);
            if(p==q) continue;
            ans+=e[i].d; f[q]=p;
            sum++; if(sum==n) break;
        }printf("%.2lf
    ",ans);
        return 0;
    }
    View Code

    2. prim 快好多啊 稠密图n^2 比 kruskal 快好多啊QAQ

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<cmath>
    using namespace std;
    const int M=1e3+7,inf=0x3f3f3f3f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,vis[M],f[M][M];
    double x[M],y[M],ans,map[M][M],d[M];
    double calc(int p,int q){return sqrt((x[p]-x[q])*(x[p]-x[q])+(y[p]-y[q])*(y[p]-y[q]));}
    void prim(){
        d[1]=0; vis[1]=1;
        for(int i=2;i<=n;i++) d[i]=map[1][i];
        for(int i=2;i<=n;i++){
            double mn=inf;
            int h=0;
            for(int j=2;j<=n;j++) if(!vis[j]&&mn>d[j]) mn=d[j],h=j;
            ans+=mn; d[h]=0; vis[h]=1;
            for(int j=2;j<=n;j++) if(!vis[j]&&map[h][j]<d[j]) d[j]=map[h][j];
        }
    }
    int main()
    {
        int p,q;
        n=read(); m=read();
        for(int i=1;i<=n;i++) scanf("%lf %lf",&x[i],&y[i]);
        for(int i=1;i<=m;i++){
            p=read(); q=read();
            f[p][q]=f[q][p]=1;
        }
        for(int i=1;i<=n;i++)
            for(int j=i+1;j<=n;j++)if(!f[i][j])
                map[i][j]=map[j][i]=calc(i,j);
        prim();
        printf("%.2lf
    ",ans);
        return 0;
    }
    View Code

     bzoj 1717: [Usaco2006 Dec]Milk Patterns 产奶的模式

    又一个代填的坑QAQ 

    这又是一道能用hash填的坑 我们可以二分答案 然后用hash套hash的方法写辣 复杂度nlongn

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #define LL unsigned long long
    const int M=45007,P=9875321,mod=1e5+7;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,k;
    LL w[M],f[M];
    int first[mod],cnt,ans[M];
    struct node{LL v; int next;}e[M];
    int find(LL x){
        LL w=x%mod;
        for(int i=first[w];i;i=e[i].next)if(e[i].v==x) return i;
        e[++cnt]=(node){x,first[w]}; first[w]=cnt;
        return cnt;
    }
    bool check(int l){
        cnt=0;
        memset(first,0,sizeof(first));
        memset(ans,0,sizeof(ans));
        for(int i=1;i<=n-l+1;i++){
            LL ly=f[i+l-1]-f[i-1]*w[l];
            int s=find(ly);
            ans[s]++;
            if(ans[s]>=k) return 1;
        }
        return 0;
    }
    int main(){
        n=read(); k=read();
        w[0]=1; for(int i=1;i<=n;i++) w[i]=w[i-1]*P;
        for(int i=1;i<=n;i++) f[i]=f[i-1]*P+read();
        if(k==0) return printf("%d
    ",n),0;
        int l=0,r=n;
        while(l<r){
            int mid=(l+r+1)>>1;
            if(check(mid)) l=mid;
            else r=mid-1;
        }printf("%d
    ",l);
        return 0;
    }
    View Code

    【bzoj1611】[Usaco2008 Feb]Meteor Shower流星雨-bfs

    小心数组越界QAQ

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    using namespace std;
    const int M=55007,inf=0x3f3f3f3f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f; 
    }
    int n,xx[5]={0,0,1,0,-1},yy[5]={0,1,0,-1,0};
    int map[307][307],vis[307][307];
    struct node{int x,y,T;};
    queue<node>q;
    int main()
    {
        for(int i=0;i<=305;i++) for(int j=0;j<=305;j++) map[i][j]=inf;
        int x,y,h;
        n=read();
        for(int i=1;i<=n;i++){
            x=read(); y=read(); 
            h=read(); map[x][y]=min(map[x][y],h);
            for(int k=1;k<=4;k++){
                int nx=x+xx[k],ny=y+yy[k];
                if(nx<0||ny<0) continue;//小心数组越界 
                map[nx][ny]=min(map[nx][ny],h);
            }
        }
        if(!map[0][0]) return printf("-1
    "),0;
        vis[0][0]=1;
        q.push((node){0,0,0});
        while(!q.empty()){
            node s=q.front(); q.pop();
            if(map[s.x][s.y]==inf) return printf("%d
    ",s.T),0;
            for(int k=1;k<=4;k++){
                int nx=s.x+xx[k],ny=s.y+yy[k],nowh=s.T+1;
                if(nx<0||ny<0||map[nx][ny]<=nowh||vis[nx][ny]) continue;
                vis[nx][ny]=1; 
                q.push((node){nx,ny,nowh});
            }
        }printf("-1
    ");
        return 0;
    }
    View Code

     bzoj 1724: [Usaco2006 Nov]Fence Repair 切割木板

    切割的逆过程就是合并 所以切割木板=合并果子

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    #define LL long long
    using namespace std;
    LL read(){
        LL ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    LL n,k,ans;
    struct node{
        LL w;
        bool operator <(const node& x)const {return x.w<w;}
    };
    priority_queue<node>q;
    int main()
    {
        n=read();
        for(int i=1;i<=n;i++) k=read(),q.push((node){k});
        for(int i=1;i<n;i++){
            node x=q.top(); q.pop();
            node y=q.top(); q.pop();
            int h=x.w+y.w;
            ans+=h;
            q.push((node){h});
        }printf("%lld
    ",ans);
        return 0;
    }
    View Code

     bzoj 1621: [Usaco2008 Open]Roads Around The Farm分岔路口——模拟

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    #define LL long long
    using namespace std;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,k,ans;
    queue<int>q;
    int main()
    {
        n=read(); k=read();
        q.push(n);
        while(!q.empty()){
            int x=q.front(); q.pop();
            if(x>k&&(x-k)%2==0){
                int now1=(x-k)/2,now2=now1+k;
                q.push(now1);
                q.push(now2);
            }
            else ans++;
        }printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj 1669: [Usaco2006 Oct]Hungry Cows饥饿的奶牛-二分求最长上升子序列

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    #define LL long long
    using namespace std;
    const int M=5007;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,k,d,q[M],cnt;
    int find(int w){
        int l=0,r=cnt;
        while(l<=r){
            int mid=(l+r)>>1;
            if(q[mid]<w) l=mid+1;
            else r=mid-1;
        }
        return l;
    }
    int main()
    {
        n=read(); 
        k=read(); q[++cnt]=k;
        for(int i=2;i<=n;i++){
            k=read(); 
            if(q[cnt]<k) q[++cnt]=k;
            else d=find(k),q[d]=k;
        }printf("%d
    ",cnt);
        return 0;
    }
    View Code

     bzoj 1232: [Usaco2008Nov]安慰奶牛cheer——最小生成树 

    每条边的权值就是他的两个端点的c+他的长度*2

    当然要记得选一个权值最小的点当作跟

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    const int M=10007,inf=0x3f3f3f3f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int ans=inf,n,m,first[M],cnt,c[M],f[M];
    int find(int x){return f[x]==x?x:f[x]=find(f[x]);}
    struct node{int from,to,w,next;}e[15*M];
    bool cmp(node a,node b){return a.w<b.w;}
    void ins(int a,int b,int w){e[++cnt]=(node){a,b,w,first[a]}; first[a]=cnt;}
    int main()
    {
        int x,y,w;
        n=read(); m=read();
        for(int i=1;i<=n;i++) c[i]=read(),f[i]=i,ans=min(ans,c[i]);
        for(int i=1;i<=m;i++) x=read(),y=read(),w=read(),ins(x,y,(w<<1)+c[x]+c[y]);
        sort(e+1,e+1+cnt,cmp);
        int h=0; 
        for(int i=1;i<=m;i++){
            int p=find(e[i].from),q=find(e[i].to);
            if(p==q) continue;
            f[q]=p; ans+=e[i].w; 
            h++; if(h==n-1) break;
        }printf("%d
    ",ans);
    }
    View Code

     bzoj 1636: [Usaco2007 Jan]Balanced Lineup-zkw线段树

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    const int N=1<<19,inf=0x3f3f3f3f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,q,l,r;
    int mx[N<<1],mn[N<<1];
    int push_ans(int l,int r){
        int mx1=0,mn1=inf;
        for(l+=N-1,r+=N+1;r-l!=1;l>>=1,r>>=1){
            if(~l&1) mx1=max(mx1,mx[l^1]),mn1=min(mn1,mn[l^1]);
            if(r&1)     mx1=max(mx1,mx[r^1]),mn1=min(mn1,mn[r^1]);
        }
        return mx1-mn1;
    }
    int main()
    {
        n=read(); q=read();
        for(int i=1;i<=n;i++) mx[N+i]=mn[N+i]=read();
        for(int i=N-1;i;i--) mx[i]=max(mx[i<<1],mx[i<<1^1]),mn[i]=min(mn[i<<1],mn[i<<1^1]);
        for(int i=1;i<=q;i++){
            l=read(); r=read();
            printf("%d
    ",push_ans(l,r));
        }
        return 0;
    }
    View Code

     bzoj 1618: [Usaco2008 Nov]Buying Hay 购买干草——完全背包

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #define LL long long
    using namespace std;
    const int inf=0x3f3f3f3f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    } 
    int n,h,mx,ans=inf;
    int f[55007];
    int c[107],w[107];
    int main()
    {
        n=read(); h=read();
        for(int i=1;i<=n;i++) c[i]=read(),w[i]=read(),mx=max(mx,c[i]);
        memset(f,0x3f,sizeof(f)); f[0]=0;
        for(int i=1;i<=n;i++)
            for(int j=c[i];j<h+mx;j++)
                f[j]=min(f[j],f[j-c[i]]+w[i]);
        for(int i=0;i<mx;i++) ans=min(ans,f[h+i]);
        printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj 1572: [Usaco2009 Open]工作安排Job——贪心+堆

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    #define LL long long
    using namespace std;
    const int M=100007;
    LL read(){
        LL ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    } 
    LL n,cnt,ans;
    struct pos{LL d,w;}e[M];
    bool cmp(pos a,pos b){return a.d<b.d;}
    priority_queue<LL>q;
    int main()
    {
        n=read();
        for(int i=1;i<=n;i++) e[i].d=read(),e[i].w=read();
        sort(e+1,e+1+n,cmp);
        for(int i=1;i<=n;i++){
            ans+=e[i].w; q.push(-e[i].w); cnt++;
            if(cnt>e[i].d) cnt--,ans+=q.top(),q.pop();
        }printf("%lld
    ",ans);
        return 0;
    }
    View Code

     bzoj 1631: [Usaco2007 Feb]Cow Party——spfa

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    using namespace std;
    const int N=1007,M=150007,inf=0x3f3f3f3f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,k;
    int first[N],cnt,star[N],cntq;
    struct node{int to,next,w;}e[M],q[M];
    void ins(int a,int b,int w){e[++cnt]=(node){b,first[a],w}; first[a]=cnt;}
    void insq(int a,int b,int w){q[++cntq]=(node){b,star[a],w}; star[a]=cnt;}
    int d1[N],d2[N],vis[N];
    queue<int>qu;
    void spfa1(){
        memset(d1,0x3f,sizeof(d1));
        d1[k]=0; vis[k]=1; qu.push(k);
        while(!qu.empty()){
            int x=qu.front(); vis[x]=0; qu.pop();
            for(int i=first[x];i;i=e[i].next){
                int now=e[i].to;
                if(d1[now]>d1[x]+e[i].w){
                    d1[now]=d1[x]+e[i].w;
                    if(!vis[now]) qu.push(now),vis[now]=1;
                }
            } 
        }
    }
    void spfa2(){
        memset(d2,0x3f,sizeof(d2));
        d2[k]=0; vis[k]=1; qu.push(k);
        while(!qu.empty()){
            int x=qu.front(); vis[x]=0; qu.pop();
            for(int i=star[x];i;i=q[i].next){
                int now=q[i].to;
                if(d2[now]>d2[x]+q[i].w){
                    d2[now]=d2[x]+q[i].w;
                    if(!vis[now]) qu.push(now),vis[now]=1;
                }
            } 
        }
    }
    int main()
    {
        int x,y,w;
        n=read(); m=read(); k=read();
        for(int i=1;i<=m;i++) x=read(),y=read(),w=read(),ins(x,y,w),insq(y,x,w);
        spfa1();
        spfa2();
        int ans=0;
        for(int i=1;i<=n;i++) ans=max(ans,d1[i]+d2[i]);
        printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj 1231: [Usaco2008 Nov]mixup2 混乱的奶牛——状压dp

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<cmath>
    #define LL long long
    using namespace std;
    LL read(){
        LL ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int s,n,mn;
    LL f[20][1<<16],h[25],w[25];
    int main()
    {
        n=read(); mn=read(); s=(1<<n)-1;
        for(int i=1;i<=n;i++) h[i]=read(),w[i]=1<<(i-1),f[i][w[i]]=1;
        for(int k=1;k<=s;k++)
            for(int i=1;i<=n;i++)if(!(k&w[i]))
                for(int j=1;j<=n;j++)if((k&w[j])&&abs(h[i]-h[j])>mn)
                    f[i][k|w[i]]+=f[j][k];
        LL ans=0;
        for(int i=1;i<=n;i++) ans+=f[i][s];
        printf("%lld
    ",ans); 
        return 0;
    }
    View Code

     bzoj 1726: [Usaco2006 Nov]Roadblocks第二短路——spfa求次短路

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    #define LL long long
    using namespace std;
    const int M=5007,inf=0x3f3f3f3f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m;
    int first[M],cnt;
    struct node{int to,next,w;}e[250007];
    void ins(int a,int b,int w){e[++cnt]=(node){b,first[a],w}; first[a]=cnt;}
    void insert(int a,int b,int w){ins(a,b,w); ins(b,a,w);}
    int d1[M],d2[M],vis[M];
    queue<int>q;
    void spfa(){
        memset(d1,0x3f,sizeof(d1));
        memset(d2,0x3f,sizeof(d2));
        d1[1]=0; vis[1]=0; q.push(1);
        while(!q.empty()){
            int x=q.front(); q.pop();
            for(int i=first[x];i;i=e[i].next){
                bool f=false;
                int now=e[i].to;
                if(d1[x]+e[i].w<d1[now]) f=true,d2[now]=min(d1[now],d2[x]+e[i].w),d1[now]=d1[x]+e[i].w;
                else if(d1[x]+e[i].w>d1[now]&&d1[x]+e[i].w<d2[now]) f=true,d2[now]=d1[x]+e[i].w;
                else if(d2[x]+e[i].w<d2[now]) f=true,d2[now]=d2[x]+e[i].w;
                if(f&&!vis[now]) vis[now]=1,q.push(now);
            }
            vis[x]=0;
        }
    }
    int main()
    {
        int x,y,w;
        n=read(); m=read();
        for(int i=1;i<=m;i++) x=read(),y=read(),w=read(),insert(x,y,w);
        spfa();
        printf("%d
    ",d2[n]);
        return 0;
    }
    View Code

     bzoj 1677: [Usaco2005 Jan]Sumsets 求和——完全背包

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    const int mod=1e9,M=1e6+7;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,f[M];
    int main()
    {
        n=read();
        f[0]=1;
        for(int i=0;(1<<i)<=n;i++){
            int now=1<<i;
            for(int j=now;j<=n;j++) (f[j]+=f[j-now])%=mod;
        }printf("%d
    ",f[n]);
        return 0;
    }
    View Code

     bzoj 1657: [Usaco2006 Mar]Mooo 奶牛的歌声——单调栈

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    using namespace std;
    const int M=50007;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,h[M],v[M];
    int st[M],top,s[M],ans;
    int main()
    {
        n=read();
        for(int i=1;i<=n;i++) h[i]=read(),v[i]=read();
        for(int i=1;i<=n;i++){
            while(top&&h[st[top]]<h[i]) s[i]+=v[st[top--]];
            st[++top]=i;
        }
        top=0;
        for(int i=n;i;i--){
            while(top&&h[st[top]]<h[i]) s[i]+=v[st[top--]];
            st[++top]=i;
        }
        for(int i=1;i<=n;i++) ans=max(ans,s[i]);
        printf("%d
    ",ans);
        return 0;
    }
    View Code

    bzoj 1646: [Usaco2007 Open]Catch That Cow 抓住那只牛——bfs

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    using namespace std;
    const int mx=100000;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int s,k,now,d[mx+7];
    queue<int>q;
    int main()
    {
        s=read(); k=read();
        q.push(s); d[s]=1;
        if(s>=k) return printf("%d
    ",s-k),0;
        while(!q.empty()){
            int x=q.front(); q.pop();
            now=x+1;if(now>=0&&now<=mx&&!d[now]) d[now]=d[x]+1,q.push(now);
            now=x-1;if(now>=0&&now<=mx&&!d[now]) d[now]=d[x]+1,q.push(now);
            now=2*x;if(now>=0&&now<=mx&&!d[now]) d[now]=d[x]+1,q.push(now);
            if(d[k]) return printf("%d
    ",d[k]-1),0;
        }
        return 0;
    }
    View Code

     bzoj 1660: [Usaco2006 Nov]Bad Hair Day 乱发节——单调栈

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    #define LL long long
    using namespace std;
    const int M=1e5+7;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int h[M],n;
    LL ans;
    int st[M],top;
    int main()
    {
        n=read();
        for(int i=1;i<=n;i++) h[i]=read();
        for(int i=1;i<=n;i++){
            while(top&&h[st[top]]<=h[i]) top--;
            ans+=top; st[++top]=i;
        }printf("%lld
    ",ans);
        return 0;
    }
    View Code

     bzoj 1734: [Usaco2005 feb]Aggressive cows 愤怒的牛——二分

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    #define LL long long
    using namespace std;
    const int M=1e5+7;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,x[M];
    int check(int k){
        int sum=x[1],cnt=1;
        for(int i=2;i<=n;i++)if(x[i]-sum>=k) cnt++,sum=x[i];
        return cnt>=m;
    }
    int main()
    {
        n=read(); m=read();
        for(int i=1;i<=n;i++) x[i]=read();
        sort(x+1,x+1+n);
        int l=0,r=x[n];
        while(l<=r){
            int mid=(l+r)>>1;
            if(check(mid)) l=mid+1;
            else r=mid-1;
        }printf("%d
    ",r);
        return 0;
    }
    View Code

     bzoj 1679: [Usaco2005 Jan]Moo Volume 牛的呼声——排序

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    #define LL long long
    using namespace std;
    const int M=1e4+7;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,x[M];
    LL ans;
    int main()
    {
        n=read(); 
        for(int i=1;i<=n;i++) x[i]=read();
        sort(x+1,x+1+n);
        LL sum=x[1];
        for(int i=2;i<=n;i++) ans=ans+1LL*(i-1)*x[i]-sum,sum+=x[i];
        printf("%lld
    ",ans*2);
        return 0;
    }
    View Code

     bzoj 1579: [Usaco2009 Feb]Revamping Trails 道路升级——分层图+Dijkstra

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    #define LL long long
    using namespace std;
    const int N=10007,inf=0x7f7f7f7f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,k;
    int d[N][25];
    struct node{
        int d,h,pos;
        bool operator <(const node& x)const{return x.d<d;}
    };
    priority_queue<node>q;
    int first[N],cnt;
    struct pos{int to,next,w;}e[10*N];
    void ins(int a,int b,int w){e[++cnt]=(pos){b,first[a],w}; first[a]=cnt;}
    void insert(int a,int b,int w){ins(a,b,w); ins(b,a,w);}
    int dj(){
        memset(d,0x7f,sizeof(d));
        for(int i=0;i<=k;i++) d[1][i]=0; 
        q.push((node){0,0,1});
        while(!q.empty()){
            node p=q.top(); q.pop();
            if(d[p.pos][p.h]!=p.d) continue;
            if(p.pos==n) return p.d;
            int x=p.pos,h=p.h;
            for(int i=first[x];i;i=e[i].next){
                int now=e[i].to;
                if(d[now][h]>d[x][h]+e[i].w) d[now][h]=d[x][h]+e[i].w,q.push((node){d[now][h],h,now});
                if(h<k&&d[now][h+1]>d[x][h]) d[now][h+1]=d[x][h],q.push((node){d[now][h+1],h+1,now});
            }
        }
        return d[n][k];
    }
    int main()
    {
        int x,y,v;
        n=read(); m=read(); k=read();
        for(int i=1;i<=m;i++) x=read(),y=read(),v=read(),insert(x,y,v);
        printf("%d
    ",dj());
        return 0;
    }
    View Code

     bzoj 1711: [Usaco2007 Open]Dining吃饭——网络流

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    #define LL long long
    using namespace std;
    const int M=1e3+7,inf=0x3f3f3f3f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,k;
    int S,T,N,ans;
    int first[M],cur[M],cnt=1;
    struct node{int to,next,flow;}e[M*M];
    void ins(int a,int b,int flow){e[++cnt]=(node){b,first[a],flow}; first[a]=cnt;}
    void insert(int a,int b,int flow){ins(a,b,flow); ins(b,a,0);}
    int d[M];
    queue<int>q;
    int bfs(){
        memset(d,-1,sizeof(d));
        d[S]=1; q.push(S);
        while(!q.empty()){
            int x=q.front(); q.pop();
            for(int i=first[x];i;i=e[i].next){
                int now=e[i].to;
                if(e[i].flow&&d[now]==-1) d[now]=d[x]+1,q.push(now);
            }
        }
        return d[T]!=-1;
    }
    int dfs(int x,int a){
        if(x==T||a==0) return a;
        int flow=0,f;
        for(int i=first[x];i;i=e[i].next){
            int now=e[i].to;
            if(d[now]==d[x]+1&&(f=dfs(now,min(e[i].flow,a)))>0){
                e[i].flow-=f; e[i^1].flow+=f;
                flow+=f;
                a-=f; if(!a) break;
            }
        }
        return flow;
    }
    int main()
    {
        int x,y,v;
        n=read(); m=read(); k=read();
        S=0; T=n*2+m+k+1; N=n*2;
        for(int i=1;i<=n;i++) insert(i,i+n,1);
        for(int i=1;i<=m;i++) insert(S,i+N,1);
        for(int i=1;i<=k;i++) insert(i+N+m,T,1);
        for(int i=1;i<=n;i++){
            x=read(); y=read();
            for(int j=1;j<=x;j++) v=read(),insert(v+N,i,1);
            for(int j=1;j<=y;j++) v=read(),insert(i+n,v+N+m,1);
        }
        while(bfs()){
            for(int i=S;i<=T;i++) cur[i]=first[i];
            ans+=dfs(S,inf);
        }printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj 1651: [Usaco2006 Feb]Stall Reservations 专用牛棚——差分

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    const int M=1e6+7;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,s[M],l,r,mx;
    int main()
    {
        n=read();
        for(int i=1;i<=n;i++){
            l=read(); r=read();
            mx=max(mx,r);
            s[l]++; s[r+1]--;
        }
        int sum=0,ans=0;
        for(int i=1;i<=mx;i++) sum+=s[i],ans=max(ans,sum);
        printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj 1690: [Usaco2007 Dec]奶牛的旅行——分数规划+spfa判负环

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    const int M=1e3+7;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    bool f;
    int n,m,v[M];
    int first[M],cnt;
    struct node{int to,next,w; double h;}e[10*M];
    void ins(int a,int b,int w){e[++cnt]=(node){b,first[a],w,0}; first[a]=cnt;}
    int vis[M];
    double d[M];
    void dfs(int x){
        vis[x]=1;
        for(int i=first[x];i;i=e[i].next){
            int now=e[i].to;
            if(d[now]>d[x]+e[i].h){
                if(vis[now]){f=true; return ;}
                d[now]=d[x]+e[i].h;
                dfs(now);
            }
        }
        vis[x]=0;
    }
    bool check(double k){
        for(int i=1;i<=cnt;i++) e[i].h=k*e[i].w-v[e[i].to];
        for(int i=1;i<=n;i++) d[i]=vis[i]=0;
        f=false; 
        for(int i=1;i<=n;i++){dfs(i); if(f) return 1;}
        return 0;
    }
    int main()
    {
        int x,y,w;
        n=read(); m=read();
        for(int i=1;i<=n;i++) v[i]=read();
        for(int i=1;i<=m;i++) x=read(),y=read(),w=read(),ins(x,y,w);
        double l=0.0,r=10000;
        while(r-l>1e-3){
            double mid=(l+r)/2;
            if(check(mid)) l=mid;
            else r=mid;
        }printf("%.2f
    ",l);
        return 0;
    }
    View Code

    bzoj 1708: [Usaco2007 Oct]Money奶牛的硬币——完全背包

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #define LL long long
    using namespace std;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,c[55];
    LL f[10007];
    int main()
    {
        n=read(); m=read();
        for(int i=1;i<=n;i++) c[i]=read();
        f[0]=1;
        for(int i=1;i<=n;i++)
            for(int j=c[i];j<=m;j++)
                f[j]+=f[j-c[i]];
        printf("%lld
    ",f[m]);
        return 0;
    }
    View Code

     bzoj 1634: [Usaco2007 Jan]Protecting the Flowers 护花——贪心

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #define LL long long
    using namespace std;
    const int M=1e5+7;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n;
    struct node{
        int T,d;
        bool operator <(const node& x)const{return T*x.d<x.T*d;}
    }e[M];
    LL ans,sum;
    int main()
    {
        n=read();
        for(int i=1;i<=n;i++) e[i].T=read(),e[i].d=read(),sum+=e[i].d;
        sort(e+1,e+1+n);
        for(int i=1;i<=n;i++){
            sum-=e[i].d;
            ans+=2*e[i].T*sum;
        }printf("%lld
    ",ans);
        return 0;
    }
    View Code

     bzoj 1629: [Usaco2007 Demo]Cow Acrobats——贪心

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #define LL long long
    using namespace std;
    const int M=1e5+7;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,ans,sum;
    struct node{int w,s;}e[M];
    bool cmp(node a,node b){return b.s-a.w>a.s-b.w;}
    int main()
    {
        n=read();
        for(int i=1;i<=n;i++) e[i].w=read(),e[i].s=read();
        sort(e+1,e+1+n,cmp); 
        ans=-e[1].s; sum=e[1].w;
        for(int i=2;i<=n;i++){
            ans=max(ans,sum-e[i].s);
            sum+=e[i].w;
        }printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj 1725: [Usaco2006 Nov]Corn Fields牧场的安排——状压dp

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #define LL long long
    using namespace std;
    const int mod=1e9;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,cnt,ans;
    int s[15],f[15][20007];
    bool pd(int x){return (x&(x<<1))==0;}
    int main()
    {
        n=read(); m=read(); cnt=(1<<m)-1;
        for(int i=1;i<=n;i++) for(int j=1;j<=m;j++) s[i]=(s[i]<<1)+(read()^1);
        for(int i=0;i<=cnt;i++) if(pd(i)&&!(i&s[1])) f[1][i]=1;
        for(int i=2;i<=n;i++)
            for(int j=0;j<=cnt;j++) if(!(j&s[i])&&pd(j))
            for(int k=0;k<=cnt;k++) if(!(j&k)&&!(k&s[i-1])&&pd(k))
            (f[i][j]+=f[i-1][k])%=mod;
        for(int i=0;i<=cnt;i++) (ans+=f[n][i])%=mod;
        printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj 1620: [Usaco2008 Nov]Time Management 时间管理——贪心

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #define LL long long
    using namespace std;
    const int M=1e3+7,mod=1e9;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,ans=1e6+7;
    struct node{int T,s;}e[M];
    bool cmp(node a,node b){return a.s>b.s;}
    int main()
    {
        n=read();
        for(int i=1;i<=n;i++) e[i].T=read(),e[i].s=read();
        sort(e+1,e+1+n,cmp);
        for(int i=1;i<=n;i++) ans=min(ans,e[i].s)-e[i].T;
        if(ans<0) printf("-1
    ");
        else printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj 1827: [Usaco2010 Mar]gather 奶牛大集会——贪心

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #define LL long long
    using namespace std;
    const int M=1e6+7;
    LL read(){
        LL ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    LL n,c[M];
    LL sz[M],ans,dis[M];
    int first[M],cnt;
    struct node{int to,next; LL w;}e[2*M];
    void ins(int a,int b,LL w){e[++cnt]=(node){b,first[a],w}; first[a]=cnt;}
    void insert(int a,int b,LL w){ins(a,b,w); ins(b,a,w);}
    LL dfs(int x,int fa){
        LL sum=dis[x]*c[x];
        sz[x]=c[x];
        for(int i=first[x];i;i=e[i].next){
            int now=e[i].to; if(now==fa) continue;
            dis[now]=dis[x]+e[i].w;
            sum+=dfs(now,x);
            sz[x]+=sz[now];
        }
        return sum;
    }
    void mov(int x,int fa){
        for(int i=first[x];i;i=e[i].next){
            int now=e[i].to; if(now==fa) continue;
            if(sz[1]-2*sz[now]<0){
                ans+=e[i].w*(sz[1]-2*sz[now]);
                mov(now,x); return ;
            }
        }
    }
    int main()
    {
        LL x,y,w;
        n=read();
        for(int i=1;i<=n;i++) c[i]=read();
        for(int i=1;i<n;i++) x=read(),y=read(),w=read(),insert(x,y,w);
        ans=dfs(1,-1);
        mov(1,-1);
        printf("%lld
    ",ans);
        return 0;
    }
    View Code

     bzoj 1639: [Usaco2007 Mar]Monthly Expense 月度开支——二分

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #define LL long long
    using namespace std;
    const int M=1e5+7;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,ans,l,r;
    int w[M];
    int check(int k){
        int sum=0,cnt=1;
        for(int i=1;i<=n;i++)
            if(sum+w[i]<=k) sum+=w[i];
            else{
                sum=w[i]; cnt++;
                if(cnt>m||w[i]>k) return 0;
            }
        return 1;
    }
    int main()
    {
        n=read(); m=read();
        for(int i=1;i<=n;i++) w[i]=read(),r+=w[i];
        while(l<=r){
            int mid=(l+r)>>1;
            if(check(mid)) ans=mid,r=mid-1;
            else l=mid+1;
        }printf("%d
    ",ans);
        return 0;
    }
    View Code

     临时改变计划 silver刷不下去了QAQ 现在先刷gold

    bzoj2442: [Usaco2011 Open]修剪草坪——单调队列优化dp

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #define LL long long
    using namespace std;
    const int M=100007;
    const LL inf=1e15;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,k;
    int head,tail,q[M];
    LL ans,f[M],h[M],mn=inf;
    int main()
    {
        n=read(); k=read();
        for(int i=1;i<=n;i++) h[i]=read(),ans+=h[i];
        for(int i=1;i<=n;i++){
            f[i]=f[q[head]]+h[i];
            while(head<=tail&&f[q[tail]]>f[i]) tail--;
            q[++tail]=i;
            while(head<=tail&&i-q[head]>k) head++;
        }
        for(int i=n-k;i<=n;i++) mn=min(mn,f[i]);
        printf("%lld
    ",ans-mn);
        return 0;
    }
    View Code

     bzoj 1592: [Usaco2008 Feb]Making the Grade 路面修整——dp

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    const int M=2007;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,s[M],h[M],f[M],ff[M];
    int main()
    {
        n=read(); for(int i=1;i<=n;i++) s[i]=read(),h[i]=s[i];
        sort(h+1,h+1+n);
        for(int i=1;i<=n;i++){
            for(int j=1;j<=n;j++){
                f[j]+=abs(s[i]-h[j]);
                if(j>1) f[j]=min(f[j],f[j-1]);
            }
            for(int j=n;j;j--){
                ff[j]+=abs(s[i]-h[j]);
                if(j<n) ff[j]=min(ff[j],ff[j+1]);
            }
        }
        printf("%d
    ",min(f[n],ff[1]));
        return 0;
    }
    View Code

     bzoj 1576: [Usaco2009 Jan]安全路经Travel——dijkstra+并查集

    题解我博客有另写 请搜索bzoj 1576(记得加空格) 另外spfa会被卡

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    using namespace std;
    const int N=1e5+7,M=4e5+7,inf=0x3f3f3f3f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,ans[N];
    int f[N],fa[N];
    int find(int x){while(x!=f[x]) x=f[x]=f[f[x]]; return x;}
    int first[N],cnt,cntq;
    struct node{int from,to,next,w;}e[M],qs[M];
    bool cmp(node a,node b){return a.w<b.w;}
    void ins(int a,int b,int w){e[++cnt]=(node){a,b,first[a],w}; first[a]=cnt;}
    void insert(int a,int b,int w){ins(a,b,w); ins(b,a,w);}
    int dis[N],dep[N];
    struct Q{
        int d,pos;
        bool operator <(const Q& x)const{return x.d<d;}
    };
    priority_queue<Q>q;
    void dj(){
        memset(dis,0x3f,sizeof(dis));
        q.push((Q){0,1}); dis[1]=0;
        while(!q.empty()){
            Q p=q.top(); q.pop();
            if(p.d>dis[p.pos]) continue;
            int x=p.pos;
            for(int i=first[x];i;i=e[i].next){
                int now=e[i].to;
                if(dis[now]>dis[x]+e[i].w){
                    dis[now]=dis[x]+e[i].w;
                    dep[now]=dep[x]+1;
                    fa[now]=x;
                    q.push((Q){dis[now],now});
                }
            }
        }
        //for(int i=1;i<=n;i++) printf("[%d] ",dis[i]); printf("
    ");
    }
    int main(){
        int x,y,w;
        n=read(); m=read();
        for(int i=1;i<=n;i++) f[i]=i;
        for(int i=1;i<=m;i++) x=read(),y=read(),w=read(),insert(x,y,w);
        dj();
        for(int i=1;i<=cnt;i++){
            x=e[i].from; y=e[i].to;
            if(dep[x]<dep[y]) swap(x,y);
            if(dis[x]==dis[y]+e[i].w) continue;
            qs[++cntq]=(node){x,y,0,dis[x]+dis[y]+e[i].w};
        }
        sort(qs+1,qs+1+cntq,cmp);
        for(int i=1;i<=cntq;i++){
            x=qs[i].from; y=qs[i].to;
            while(x!=y){
                if(dep[x]<dep[y]) swap(x,y);
                if(!ans[x]) ans[x]=qs[i].w-dis[x];
                x=f[x]=find(fa[x]); //printf("[%d]
    ",x);
            }
        }    
        for(int i=2;i<=n;i++){
            if(!ans[i]) printf("-1
    ");
            else printf("%d
    ",ans[i]);
        }
        return 0;
    }
    View Code

    bzoj 1782: [Usaco2010 Feb]slowdown 慢慢游——dfs序

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    const int M=2e5+7;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,sum,l[M],r[M],pos[M],k;
    int first[M],cnt;
    struct node{int to,next;}e[2*M];
    void ins(int a,int b){e[++cnt]=(node){b,first[a]}; first[a]=cnt;}
    void insert(int a,int b){ins(a,b); ins(b,a);}
    void dfs(int x,int fa){
        pos[x]=l[x]=++sum;
        for(int i=first[x];i;i=e[i].next){
            int now=e[i].to;
            if(now==fa) continue;
            dfs(now,x);
        }
        r[x]=sum;
    }
    int s[M];
    int lowbit(int x){return x&-x;}
    int query(int x){
        int ans=0;
        while(x){ans+=s[x]; x-=lowbit(x);}
        return ans;
    }
    void add(int x,int v){
        while(x<=n){
            s[x]+=v;
            x+=lowbit(x);
        }
    }
    int main(){
        int x,y;
        n=read();
        for(int i=1;i<n;i++) x=read(),y=read(),insert(x,y);
        dfs(1,0);
        for(int i=1;i<=n;i++){
            k=read();
            int lx=l[k],rx=r[k];
            printf("%d
    ",query(pos[k]));
            add(lx,1); add(rx+1,-1);
        }
        return 0;
    }
    View Code

    bzoj 1596: [Usaco2008 Jan]电话网络——贪心+dfs

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    using namespace std;
    const int M=2e4+7;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int ans,n,mark[M];
    int first[M],cnt;
    struct node{int to,next;}e[2*M];
    void ins(int a,int b){e[++cnt]=(node){b,first[a]}; first[a]=cnt;}
    void insert(int a,int b){ins(a,b); ins(b,a);}
    void dfs(int x,int fa){
        bool f=false;
        for(int i=first[x];i;i=e[i].next){
            int now=e[i].to;
            if(now==fa) continue;
            dfs(now,x);
            if(mark[now]) f=1;
        }
        if(!f&&!mark[x]&&!mark[fa]){ans++; mark[fa]=1;}
    }
    int main(){
        int x,y;
        n=read(); for(int i=1;i<n;i++) x=read(),y=read(),insert(x,y);
        dfs(1,0);
        printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj 1692: [Usaco2007 Dec]队列变换——二分+hash

    强行hash代替后缀数组QAQ

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    const int M=35007,P=9875321;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,cnt;
    char s[M],ans[M];
    unsigned long long h1[M],h2[M],w[M];
    int find(int x,int y){
        if(s[x]!=s[y]) return 0;
        int l=1,r=y-x+1;
        while(l<r){
            int mid=(l+r)>>1;
            if(h1[x+mid]-h1[x-1]*w[mid+1]==h2[y-mid]-h2[y+1]*w[mid+1]) l=mid+1;
            else r=mid;
        }//printf("%d %d [%d]
    ",x,y,l);
        return l;
    }
    void prepare(){
        w[0]=1;
        for(int i=1;i<=n;i++) w[i]=w[i-1]*P;
    }
    int main(){
        n=read(); prepare();
        for(int i=1;i<=n;i++) scanf("%s",s+i);
        for(int i=1;i<=n;i++) h1[i]=h1[i-1]*P+s[i];
        for(int i=n;i;i--) h2[i]=h2[i+1]*P+s[i];
        int l=1,r=n;
        while(l<=r){
            int d=find(l,r);
            if(s[l+d]<s[r-d]) ans[++cnt]=s[l],l++;
            else ans[++cnt]=s[r],r--;
        }//printf("[%d]
    ",cnt);
        for(int i=1;i<=cnt;++i){
            putchar(ans[i]);
            if(i%80==0)putchar(10);
        }
        return 0;
    }
    View Code

     bzoj 1715: [Usaco2006 Dec]Wormholes 虫洞——spfa判负环

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    const int M=507;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int T,n,m,k,vis[M],d[M];
    int first[M],cnt;
    struct node{int to,next,w;}e[10007];
    void ins(int a,int b,int w){e[++cnt]=(node){b,first[a],w}; first[a]=cnt;}
    void insert(int a,int b,int w){ins(a,b,w); ins(b,a,w);}
    bool f;
    void dfs(int x){
        vis[x]=1;
        for(int i=first[x];i;i=e[i].next){
            int now=e[i].to;
            if(d[now]>d[x]+e[i].w){
                if(vis[now]){f=true; return ;}
                d[now]=d[x]+e[i].w;
                dfs(now);
            }
        }
        vis[x]=0;
    }
    int pd(){
        f=false;
        memset(vis,0,sizeof(vis));
        for(int i=1;i<=n;i++){
            memset(d,0,sizeof(d));
            dfs(i); 
            if(f) return 1;
        }
        return 0;
    }
    int main(){
        T=read();
        while(T--){
            int x,y,w;
            cnt=0; memset(first,0,sizeof(first));
            n=read(); m=read(); k=read();
            for(int i=1;i<=m;i++) x=read(),y=read(),w=read(),insert(x,y,w);
            for(int i=1;i<=k;i++) x=read(),y=read(),w=read(),ins(x,y,-w);
            if(pd()) printf("YES
    ");
            else printf("NO
    ");
        }
        return 0;
    }
    View Code

     bzoj 1596: [Usaco2008 Jan]电话网络——贪心

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    using namespace std;
    const int M=2e4+7;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int ans,n,mark[M];
    int first[M],cnt;
    struct node{int to,next;}e[2*M];
    void ins(int a,int b){e[++cnt]=(node){b,first[a]}; first[a]=cnt;}
    void insert(int a,int b){ins(a,b); ins(b,a);}
    void dfs(int x,int fa){
        bool f=false;
        for(int i=first[x];i;i=e[i].next){
            int now=e[i].to;
            if(now==fa) continue;
            dfs(now,x);
            if(mark[now]) f=1;
        }
        if(!f&&!mark[x]&&!mark[fa]){ans++; mark[fa]=1;}
    }
    int main(){
        int x,y;
        n=read(); for(int i=1;i<n;i++) x=read(),y=read(),insert(x,y);
        dfs(1,0);
        printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj 1571: [Usaco2009 Open]滑雪课Ski——dp

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    const int M=15007,N=107;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int T,n,m,ans;
    int s[M],d[M],h[M],mn[N];
    int c[M],w[M];
    int f[M][N],k[M][N],g[M][N];
    int main(){
        T=read(); n=read(); m=read();
        for(int i=1;i<=n;i++) s[i]=read(),d[i]=read(),h[i]=read(),k[s[i]+d[i]][h[i]]=s[i];
        for(int i=1;i<=m;i++) c[i]=read(),w[i]=read();
        memset(mn,0x3f,sizeof(mn));
        memset(f,-0x3f,sizeof(f));
        memset(g,-0x3f,sizeof(g));
        for(int i=1;i<=100;i++)
         for(int j=1;j<=m;j++)if(c[j]<=i) mn[i]=min(mn[i],w[j]);
        f[0][1]=g[0][1]=0;
        for(int i=1;i<=T;i++){
            for(int j=0;j<=100;j++){
                f[i][j]=f[i-1][j];
                if(i>=mn[j]) f[i][j]=max(f[i][j],f[i-mn[j]][j]+1);
                f[i][j]=max(f[i][j],g[k[i][j]][j]);
                g[i][j]=max(g[i][j-1],f[i][j]);
            }
        }
        for(int i=1;i<=100;i++) ans=max(ans,f[T][i]);
        printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj 1770: [Usaco2009 Nov]lights 燈

    1.折半搜索

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #define LL long long
    using namespace std;
    const int mod=9875321,inf=0x3f3f3f3f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int ans[1<<19],n,m,h,mn=inf;
    LL p[55],tot;
    bool f;
    int first[mod],cnt;
    struct node{LL v; int next;}e[1<<19];
    int get(LL w){
        int x=w%mod;
        for(int i=first[x];i;i=e[i].next) if(e[i].v==w) return i;
        e[++cnt]=(node){w,first[x]}; first[x]=cnt; 
        return cnt;
    }
    void dfs(int x,LL now,int step){
        if(x==h+1){
            int k;
            if(now==tot) mn=min(mn,step);
            if(!f){
                k=get(now);
                if(!ans[k]||ans[k]>step) ans[k]=step;
            }
            else{
                k=get(tot-now);
                if(!ans[k]) return ;
                mn=min(mn,ans[k]+step);
            }
            return ;
        }
        dfs(x+1,now,step);
        dfs(x+1,now^p[x],step+1);
    }
    int main(){
        int x,y;
        n=read(); m=read(); tot=(1LL<<n)-1;
        for(int i=1;i<=n;i++) p[i]=1LL<<(i-1);
        for(int i=1;i<=m;i++){
            x=read(); y=read();
            p[x]^=1LL<<(y-1); p[y]^=1LL<<(x-1);
        }
        f=false; h=n/2; dfs(1,0,0); 
        f=true;  h=n; dfs(n/2+1,0,0);
        printf("%d
    ",mn);
        return 0;
    }
    View Code

     2.高斯消元——待填

    bzoj  1668: [Usaco2006 Oct]Cow Pie Treasures 馅饼里的财富——dp(最长路)

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    const int N=107,inf=0x3f3f3f3f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,now;
    int s[N][N],d[N][N];
    int main(){
        n=read(); m=read();
        for(int i=1;i<=n;i++) for(int j=1;j<=m;j++) s[i][j]=read();
        memset(d,-0x3f,sizeof(d)); d[1][1]=s[1][1];
        for(int i=2;i<=m;i++)
            for(int j=1;j<=n;j++){
                now=j-1;if(now>=1&&now<=n) d[j][i]=max(d[j][i],d[now][i-1]+s[j][i]); 
                now=j;  if(now>=1&&now<=n) d[j][i]=max(d[j][i],d[now][i-1]+s[j][i]);
                now=j+1;if(now>=1&&now<=n) d[j][i]=max(d[j][i],d[now][i-1]+s[j][i]);
            }
        printf("%d
    ",d[n][m]);
        return 0;
    }
    View Code

     bzoj 1691: [Usaco2007 Dec]挑剔的美食家——贪心+平衡树

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<set>
    #define LL long long
    const int M=150007;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m;
    LL ans;
    struct node{
        int w,c;
        bool operator <(const node& x)const{return x.c<c;}
    }e[M],q[M];
    std::multiset<int>tr;
    std::multiset<int>::iterator it;
    int main(){
        n=read(); m=read();
        for(int i=1;i<=n;i++) e[i].w=read(),e[i].c=read();
        for(int i=1;i<=m;i++) q[i].w=read(),q[i].c=read();
        std::sort(e+1,e+1+n); 
        std::sort(q+1,q+1+m);
        int k=1;
        for(int i=1;i<=n;i++){
            while(k<=m&&q[k].c>=e[i].c) tr.insert(q[k++].w);
            it=tr.lower_bound(e[i].w);
            if(it!=tr.end()) ans+=*it,tr.erase(it);
            else return puts("-1"),0;
        }printf("%lld
    ",ans);
        return 0;
    }
    View Code

     bzoj 1593: [Usaco2008 Feb]Hotel 旅馆——线段树

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    const int M=1<<17;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int k,d,n,m,L,R;
    struct node{int l,r,lr,rl,mx,h[2];}tr[M];
    void up(int x){
        int l=x<<1,r=x<<1^1;
        tr[x].lr=tr[l].lr;    
        if(tr[l].lr==tr[l].r-tr[l].l+1) tr[x].lr=tr[l].lr+tr[r].lr;
        tr[x].rl=tr[r].rl;
        if(tr[r].rl==tr[r].r-tr[r].l+1) tr[x].rl=tr[r].rl+tr[l].rl;
        tr[x].mx=max(max(tr[l].mx,tr[r].mx),tr[l].rl+tr[r].lr);
    }
    void calc(int x){
        tr[x].lr=tr[x].rl=tr[x].mx=0;
        tr[x].h[0]=1; tr[x].h[1]=0;
    }
    void calc1(int x){
        tr[x].lr=tr[x].rl=tr[x].mx=tr[x].r-tr[x].l+1;
        tr[x].h[1]=1; tr[x].h[0]=0;
    }
    void down(int x){
        int l=x<<1,r=x<<1^1;
        if(tr[x].h[0]){        
            calc(l); calc(r);
            tr[x].h[0]=0;
        }
        if(tr[x].h[1]){
            calc1(l); calc1(r);
            tr[x].h[1]=0;
        }
    }
    void build(int x,int l,int r){
        tr[x].l=l; tr[x].r=r;
        if(l==r){
            tr[x].lr=tr[x].rl=tr[x].mx=1;
            return ;
        }
        int mid=(l+r)>>1;
        build(x<<1,l,mid);
        build(x<<1^1,mid+1,r);
        up(x);
    }
    void modify(int x,int s){
        if(L<=tr[x].l&&tr[x].r<=R){
            if(s==0) calc(x);
            else calc1(x);
            return ;
        }
        down(x);
        int mid=(tr[x].l+tr[x].r)>>1;
        if(L<=mid) modify(x<<1,s);
        if(R>mid) modify(x<<1^1,s);
        up(x);
    }
    int find(int x,int d){
        down(x); 
        int l=x<<1,r=x<<1^1,mid=(tr[x].l+tr[x].r)>>1;
        if(tr[x].l==tr[x].r) return l;
        if(tr[l].mx>=d) return find(l,d);
        if(tr[l].rl+tr[r].lr>=d) return mid-tr[l].rl+1;
        return find(r,d);
    }
    int main(){
        n=read(); m=read();
        build(1,1,n);
        for(int i=1;i<=m;i++){
            k=read();
            if(k==1){
                d=read();
                if(tr[1].mx<d) printf("0
    ");
                else{
                    int y=find(1,d);
                    printf("%d
    ",y);
                    L=y; R=y+d-1;
                    modify(1,0);
                }
            }
            else{
                L=read(); R=L+read()-1;
                modify(1,1);
            }
        }
        return 0;
    }
    View Code

     bzoj 1604: [Usaco2008 Open]Cow Neighborhoods 奶牛的邻居——排序+贪心+set

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<set>
    #include<queue>
    using namespace std;
    const int M=150007;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,c;
    int f[M],h[M],ans,mx;
    int find(int x){while(f[x]!=x) x=f[x]=f[f[x]]; return x;}
    struct node{
        int x,y,id;
        bool operator <(const node& k)const{return x<k.x;}
    }e[M];
    struct pos{
        int y,id;
        bool operator <(const pos& k)const{return y!=k.y?y<k.y:id<k.id;}
    };
    std::queue<int>q;
    std::multiset<pos>tr;
    std::multiset<pos>::iterator it;
    int main(){
        int x,y;
        n=read(); c=read();
        for(int i=1;i<=n;i++){
            x=read(); y=read();
            f[i]=i; e[i].x=x+y,e[i].y=x-y; e[i].id=i;
        }
        sort(e+1,e+1+n);
        for(int i=1;i<=n;i++){
            while(!q.empty()&&e[i].x-e[q.front()].x>c){
                int now=q.front(); q.pop();
                tr.erase(tr.find((pos){e[now].y,e[now].id}));
            }
            q.push(i);
            it=tr.insert((pos){e[i].y,e[i].id});
            if(it!=tr.begin()){
                --it;
                if(e[i].y-(it->y)<=c){
                    int p=find(e[i].id),q=find(it->id);
                    f[q]=p;
                }
                ++it;
            }
            ++it;
            if(it!=tr.end()){
                if(it->y-e[i].y<=c){
                    int p=find(e[i].id),q=find(it->id);
                    f[q]=p;
                }
            }
        }
        for(int i=1;i<=n;i++){
            int x=find(e[i].id);
            if(!h[x]) ans++;
            h[x]++; mx=max(mx,h[x]);
        }printf("%d %d
    ",ans,mx);
        return 0;
    }
    View Code

     bzoj 1697: [Usaco2007 Feb]Cow Sorting牛排序——置换

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    const int M=10007;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,v[M],s[M],vis[M],ans;
    void mins(int &x,int y){if(y<x) x=y;}
    int min(int x,int y){return x<y?x:y;}
    int main(){
        n=read();
        for(int i=1;i<=n;i++) v[i]=s[i]=read();
        sort(s+1,s+1+n);
        for(int i=1;i<=n;i++)if(!vis[i]){
            int mn=v[i],sum=v[i],now=i,h=1;
            while(1){
                vis[now=lower_bound(s+1,s+1+n,v[now])-s]=1;
                if(now==i) break;
                h++; mins(mn,v[now]);
                sum+=v[now];
            }
            ans=ans+min((sum-mn)+(h-1)*mn,(s[1]+mn)*2+(sum-mn)+(h-1)*s[1]);
        }printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj 1589: [Usaco2008 Dec]Trick or Treat on the Farm 采集糖果——拓扑排序求基环树

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    const int M=150007;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,to[M],in[M],stk[M],top,f[M];
    int head,tail,q[M];
    int main(){
        n=read();
        for(int i=1;i<=n;i++) to[i]=read(),in[to[i]]++;
        for(int i=1;i<=n;i++) if(!in[i]) q[tail++]=i;
        while(head<=tail){
            int x=q[head++],now=to[x];
            in[now]--;
            if(!in[now]) q[tail++]=now;
        }
        for(int i=1;i<=n;i++)if(in[i]){
            int now=i,h=1;
            stk[top=1]=i; in[i]=0;
            while(1){
                now=to[now];
                if(now==i) break;
                h++; in[now]=0; stk[++top]=now;
            }
            while(top) f[stk[top]]=h,top--;
        }
        while(tail>0) tail--,f[q[tail]]=f[to[q[tail]]]+1;
        for(int i=1;i<=n;i++) printf("%d
    ",f[i]);
        return 0;
    }
    View Code

     bzoj 1574: [Usaco2009 Jan]地震损坏Damage——贪心+搜索

    因为你一个点附近的点如果能够使其他点到达1那他也一定可以然这个点到达1 

    所以把走不到1的点全部删掉然后dfs一次就行了

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    const int M=35007;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,k,ans;
    int first[M],cnt,mark[M],vis[M];
    struct node{int to,next;}e[10*M];
    void ins(int a,int b){e[++cnt]=(node){b,first[a]}; first[a]=cnt;}
    void insert(int a,int b){ins(a,b); ins(b,a);}
    void delet(int x){for(int i=first[x];i;i=e[i].next) mark[e[i].to]=1;}
    void dfs(int x){
        vis[x]=1; ans--;
        for(int i=first[x];i;i=e[i].next){
            int now=e[i].to;
            if(!mark[now]&&!vis[now]) dfs(now);
        }
    }
    int main(){
        int x,y;
        n=read(); m=read(); k=read();
        for(int i=1;i<=m;i++) x=read(),y=read(),insert(x,y);
        for(int i=1;i<=k;i++) x=read(),delet(x);
        ans=n; dfs(1); 
        printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj 1707: [Usaco2007 Nov]tanning分配防晒霜——排序贪心

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<set>
    const int M=2507;
    char buf[M*44],*ptr=buf-1;
    int read(){
        int ans=0,f=1,c=*++ptr;
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=*++ptr;}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=*++ptr;}
        return ans*f;
    }
    int n,m,ans;
    struct node{
        int l,r;
        bool operator <(const node& x)const{return r<x.r;}
    }e[M];
    struct pos{
        int w,h;
        bool operator <(const pos& x)const{return w<x.w;}
    }q[M];
    struct Q{ 
        int w,id;
        bool operator <(const Q& x)const{return w!=x.w?w<x.w:id<x.id;}
    };
    std::multiset<Q>tr;
    std::multiset<Q>::iterator it;
    int main(){
        fread(buf,1,sizeof(buf),stdin);
        n=read(); m=read();
        for(int i=1;i<=n;i++) e[i].l=read(),e[i].r=read();
        std::sort(e+1,e+1+n);
        for(int i=1;i<=m;i++) q[i].w=read(),q[i].h=read();
        std::sort(q+1,q+1+m);
        int k=1;
        for(int i=1;i<=n;i++){
            while(k<=m&&q[k].w<=e[i].r) tr.insert((Q){q[k].w,k}),k++;
            it=tr.lower_bound((Q){e[i].l,-1});
            if(it!=tr.end()){
                ans++; q[it->id].h--;
                if(!q[it->id].h) tr.erase(it);
            }
        }printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj 1709: [Usaco2007 Oct]Super Paintball超级弹珠——暴力

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    const int M=157;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,k,s[9][M][M],f[M][M],ans;
    int main(){
        int x,y;
        n=read(); k=read();
        for(int i=1;i<=k;i++){
            x=read(); y=read(); f[x][y]++;
            for(int k=1;k<=8;k++) s[k][x][y]++;
        }
        for(int i=1;i<=n;i++) 
            for(int j=1;j<=n;j++){
                s[1][i][j]+=s[1][i][j-1];
                s[2][i][j]+=s[2][i-1][j-1];
                s[3][i][j]+=s[3][i-1][j];
                s[4][i][j]+=s[4][i-1][j+1];
            }
        for(int i=n;i;i--)
            for(int j=n;j;j--){
                s[5][i][j]+=s[5][i][j+1];
                s[6][i][j]+=s[6][i+1][j-1];
                s[7][i][j]+=s[7][i+1][j];
                s[8][i][j]+=s[8][i+1][j+1];
            }
        for(int i=1;i<=n;i++)
            for(int j=1;j<=n;j++){
                for(int k=1;k<=8;k++) s[0][i][j]+=s[k][i][j];
                if(f[i][j]) s[0][i][j]-=7*f[i][j];
            }
        for(int i=1;i<=n;i++)
            for(int j=1;j<=n;j++)if(s[0][i][j]==k) ans++;
        printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj 1828: [Usaco2010 Mar]balloc 农场分配——线段树

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    const int M=1e5+7,N=1<<18,inf=0x3f3f3f3f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,ans,L,R;
    struct node{int l,r;}q[M];
    bool cmp(node a,node b){return a.r!=b.r?a.r<b.r:a.l>b.l;}
    struct pos{int l,r,mn,tag;}tr[N];
    void up(int x){tr[x].mn=std::min(tr[x<<1].mn,tr[x<<1^1].mn);}
    void down(int x){
        if(tr[x].tag){
            int v=tr[x].tag; tr[x].tag=0;
            tr[x<<1].tag+=v; tr[x<<1^1].tag+=v;
            tr[x<<1].mn-=v;  tr[x<<1^1].mn-=v;
        }
    }
    void build(int x,int l,int r){
        tr[x].l=l; tr[x].r=r; 
        if(l==r){tr[x].mn=read();return ;}
        int mid=(l+r)>>1;
        build(x<<1,l,mid);
        build(x<<1^1,mid+1,r);
        up(x);
    }
    int pmin(int x){
        if(L<=tr[x].l&&tr[x].r<=R) return tr[x].mn;
        int mid=(tr[x].l+tr[x].r)>>1,mn=inf;
        down(x);
        if(L<=mid) mn=std::min(mn,pmin(x<<1));
        if(R>mid) mn=std::min(mn,pmin(x<<1^1));
        return mn;
    }
    void modify(int x){
        if(L<=tr[x].l&&tr[x].r<=R){tr[x].mn-=1; tr[x].tag++; return ;}
        int mid=(tr[x].l+tr[x].r)>>1;
        down(x);
        if(L<=mid) modify(x<<1);
        if(R>mid) modify(x<<1^1);
        up(x);
    }
    int main(){
        n=read(); m=read();
        build(1,1,n);
        for(int i=1;i<=m;i++) q[i].l=read(),q[i].r=read();
        std::sort(q+1,q+1+m,cmp);
        for(int i=1;i<=m;i++){
            L=q[i].l; R=q[i].r;
            if(pmin(1)>=1) ans++,modify(1);
        }printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj 1706: [usaco2007 Nov]relays 奶牛接力跑——倍增floyd(裸

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    const int M=1e3+7,inf=0x3f3f3f3f,mod=29399;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,S,T;
    int first[mod],cnt;
    struct node{int v,next;}e[M];
    int get(int w){
        int x=w%mod;
        for(int i=first[x];i;i=e[i].next) if(e[i].v==w) return i;
        e[++cnt]=(node){w,first[x]}; first[x]=cnt; return cnt;
    }
    void mins(int &x,int y){if(x>y) x=y;}
    typedef int mat[M][M];
    mat f,ans,tmp;
    void floyd(mat b,mat c){
        memset(tmp,0x3f,sizeof(mat));
        for(int i=1;i<=cnt;i++)
        for(int k=1;k<=cnt;k++)
        for(int j=1;j<=cnt;j++) mins(tmp[i][j],b[i][k]+c[k][j]);
        memcpy(b,tmp,sizeof(mat));
    }
    int main(){
        int x,y,w;
        memset(f,0x3f,sizeof(mat));
        n=read(); m=read(); S=get(read()); T=get(read());
        for(int i=1;i<=m;i++) w=read(),x=get(read()),y=get(read()),f[x][y]=f[y][x]=std::min(f[x][y],w);
        memset(ans,0x3f,sizeof(mat));
        for(int i=1;i<=cnt;i++) ans[i][i]=0;
        for(;n;n>>=1,floyd(f,f)) if(n&1) floyd(ans,f);
        printf("%d
    ",ans[S][T]);
        return 0;
    }
    View Code

     bzoj 1584: [Usaco2009 Mar]Cleaning Up 打扫卫生——$nsqrt(n)$ DP

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<cmath>
    #define LL long long
    const int M=40007;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,d;
    int c[M],last[M],now[M],q[M],f[M];
    void mins(int &x,int y){if(x>y) x=y;}
    int main(){
        n=read(); m=read(); d=sqrt(n);
        for(int i=1;i<=m;i++) last[i]=-1;
        for(int i=1;i<=n;i++) c[i]=read(),now[i]=last[c[i]],last[c[i]]=i;
        for(int i=1;i<=n;i++){
            int k=1; while(k<=d&&q[k]>now[i]) k++; k--;
            f[i]=i; q[0]=i;
            for(int j=std::min(k,d);j;j--) q[j]=q[j-1];
            for(int j=1;j<=d;j++) mins(f[i],f[q[j]-1]+j*j);
        }printf("%d
    ",f[n]);
        return 0;
    }
    View Code

     bzoj 1754: [Usaco2005 qua]Bull Math——高精度x高精度

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    const int M=55;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    char s1[M],s2[M];
    int cnt1,cnt2,b[M],c[M],ans[2*M],cntq;
    int main(){
        scanf("%s%s",s1,s2);
        cnt1=strlen(s1); cnt2=strlen(s2);
        for(int i=0;i<cnt1;++i) b[i]=s1[cnt1-i-1]-'0';
        for(int i=0;i<cnt2;++i) c[i]=s2[cnt2-i-1]-'0';
        cntq=cnt1+cnt2;
        for(int i=0;i<cnt1;--i){
            for(int j=0;j<cnt2;j++){
                ans[i+j]+=b[i]*c[j];
            }
        }
        for(int i=0;i<cntq;++i){
            ans[i+1]+=ans[i]/10;
            ans[i]%=10;
        }
        while(!ans[cntq]&&cntq) --cntq;
        for(int i=cntq;i>=0;--i) printf("%d",ans[i]);
        return 0;
    }
    View Code

     bzoj 1753: [Usaco2005 qua]Who's in the Middle——STL nth_element

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    const int M=10007;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,k,s[M];
    int main(){
        n=read(); k=n/2;
        for(int i=0;i<n;i++) s[i]=read();
        std::nth_element(s,s+k,s+n);
        printf("%d
    ",s[k]);
        return 0;
    }
    View Code

     bzoj 1710: [Usaco2007 Open]Cheappal 廉价回文——dp

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using std::min;
    const int M=3e3+7;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,cnt;
    int f[M][35],cost[M];
    char s[M],ch[15];
    int main(){
        int x,y;
        n=read(); m=read();
        scanf("%s",s+1); cnt=strlen(s+1);
        for(int i=1;i<=n;i++){
            scanf("%s",ch); x=read(); y=read();
            cost[(int)ch[0]]=min(x,y);
        }
        for(int k=1;k<m;k++){
            for(int l=1;l<=m-k;l++){
                int r=l+k;
                f[l][r]=min(f[l+1][r]+cost[(int)s[l]],f[l][r-1]+cost[(int)s[r]]);
                if(s[l]==s[r]) f[l][r]=min(f[l][r],f[l+1][r-1]);
            }
        }printf("%d
    ",f[1][m]);
        return 0;
    }
    View Code

     bzoj 1598: [Usaco2008 Mar]牛跑步——第K短路

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    const int M=2e3+7,inf=0x3f3f3f3f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,k,h[M],d[M][105];
    int first[M],cnt;
    struct node{int to,next,w;}e[10*M];
    void ins(int a,int b,int w){e[++cnt]=(node){b,first[a],w}; first[a]=cnt;}
    void merge(int s1[M],int s2[M],int w){
        memset(h,0,sizeof(h));
        int cnt=0,l=1,r=1;
        while(cnt<k){
            if(s1[l]<s2[r]+w) h[++cnt]=s1[l++];
            else h[++cnt]=s2[r]+w,r++;
        }
        for(int i=1;i<=k;i++) s1[i]=h[i];
    }
    int main(){
        int x,y,w;
        n=read(); m=read(); k=read();
        for(int i=1;i<=m;i++) x=read(),y=read(),w=read(),ins(y,x,w);
        memset(d,0x3f,sizeof(d));
        d[n][1]=0;
        for(int x=n-1;x;x--){
            for(int i=first[x];i;i=e[i].next){
                int now=e[i].to;
                merge(d[x],d[now],e[i].w);
            }
        }
        for(int i=1;i<=k;i++) 
            if(d[1][i]==inf) printf("-1
    ");
            else printf("%d
    ",d[1][i]);
        return 0;
    }
    View Code

    bzoj 2060: [Usaco2010 Nov]Visiting Cows 拜访奶牛——树形dp

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using std::max;
    const int M=50007;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,f[M][2];
    int first[M],cnt;
    struct node{int to,next;}e[2*M];
    void ins(int a,int b){e[++cnt]=(node){b,first[a]}; first[a]=cnt;}
    void insert(int a,int b){ins(a,b); ins(b,a);}
    void dfs(int x,int fa){
        f[x][1]=1;
        for(int i=first[x];i;i=e[i].next){
            int now=e[i].to;
            if(now==fa) continue;
            dfs(now,x);
            f[x][0]=f[x][0]+max(f[now][0],f[now][1]);
            f[x][1]=f[x][1]+f[now][0];
        }
    }
    int main(){
        int x,y;
        n=read();
        for(int i=1;i<n;i++) x=read(),y=read(),insert(x,y);
        dfs(1,-1);
        printf("%d
    ",max(f[1][0],f[1][1]));
        return 0;
    }
    View Code

    bzoj 1741: [Usaco2005 nov]Asteroids 穿越小行星群——网络流

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    using std::min;
    const int M=2e3+7,inf=0x3f3f3f3f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,k,cur[M],d[M];
    int S,T,ans;
    int first[M],cnt=1;
    struct node{int to,next,flow;}e[20*M];
    void ins(int a,int b,int flow){e[++cnt]=(node){b,first[a],flow}; first[a]=cnt;}
    void insert(int a,int b,int flow){ins(a,b,flow); ins(b,a,0);}
    std::queue<int>q;
    int bfs(){
        memset(d,-1,sizeof(d));
        d[S]=1; q.push(S);
        while(!q.empty()){
            int x=q.front(); q.pop();
            for(int i=first[x];i;i=e[i].next){
                int now=e[i].to;
                if(e[i].flow&&d[now]==-1) d[now]=d[x]+1,q.push(now); 
            }
        }
        return d[T]!=-1;
    }
    int dfs(int x,int a){
        if(x==T||a==0) return a;
        int flow=0,f;
        for(int& i=cur[x];i;i=e[i].next){
            int now=e[i].to;
            if(d[now]==d[x]+1&&(f=dfs(now,min(e[i].flow,a)))>0){
                e[i].flow-=f; e[i^1].flow+=f;
                flow+=f;
                a-=f; if(!a) break;
            }
        }
        return flow;
    }
    int main(){
        int x,y;
        n=read(); k=read();
        S=0; T=2*n+1;
        for(int i=1;i<=n;i++) insert(S,i,1);
        for(int i=1;i<=n;i++) insert(i+n,T,1);
        for(int i=1;i<=k;i++) x=read(),y=read(),insert(x,y+n,1);
        while(bfs()){for(int i=S;i<=T;i++) cur[i]=first[i]; ans+=dfs(S,inf);}
        printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj 1703: [Usaco2007 Mar]Ranking the Cows 奶牛排名——floyd传递闭包

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<bitset>
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,x,y,ans;
    std::bitset<1007> f[1007];
    int main(){
        n=read(); m=read();
        for(int i=1;i<=m;i++) x=read(),y=read(),f[x][y]=1;
        for(int k=1;k<=n;k++)
         for(int i=1;i<=n;i++)
             if(f[i][k]) f[i]|=f[k];
        for(int i=1;i<=n;i++)
            for(int j=i+1;j<=n;j++)if(!f[i][j]&&!f[j][i]) ans++;
        printf("%d
    ",ans);
        return 0;
    }
    View Code

    bzoj 1578: [Usaco2009 Feb]Stock Market 股票市场——dp(完全背包

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using std::max;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,k,mx;
    int f[550007],map[105][105];
    int main(){
        n=read(); m=read(); k=read();
        for(int i=1;i<=n;i++) for(int j=1;j<=m;j++) map[j][i]=read();
        mx=k;
        for(int i=2;i<=m;i++){
            memset(f,0,sizeof(f));
            for(int j=1;j<=n;j++)
            {
            //printf("%d %dQWQ
    ",map[i-1][j],mx);
            for(int k=map[i-1][j];k<=mx;k++)
            f[k]=max(f[k],f[k-map[i-1][j]]+(map[i][j]-map[i-1][j]));
            }
            mx+=f[mx];
            //printf("QAQ%d
    ",mx);
        }
        printf("%d
    ",mx);
        return 0;
    }
    View Code

     bzoj 1703: [Usaco2007 Mar]Ranking the Cows 奶牛排名——floyd传递闭包

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<bitset>
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,x,y,ans;
    std::bitset<1007> f[1007];
    int main(){
        n=read(); m=read();
        for(int i=1;i<=m;i++) x=read(),y=read(),f[x][y]=1;
        for(int k=1;k<=n;k++)
         for(int i=1;i<=n;i++)
             if(f[i][k]) f[i]|=f[k];
        for(int i=1;i<=n;i++)
            for(int j=i+1;j<=n;j++)if(!f[i][j]&&!f[j][i]) ans++;
        printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj 1585: [Usaco2009 Mar]Earthquake Damage 2 地震伤害——最小割

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    const int M=25007,inf=0x3f3f3f3f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int first[M],cur[M],cnt=1,ans;
    int n,m,h,S,T,mark[M];
    struct node{int to,next,flow;}e[10*M];
    void ins(int a,int b,int flow){e[++cnt]=(node){b,first[a],flow}; first[a]=cnt;}
    void insert(int a,int b,int flow){ins(a,b,flow); ins(b,a,0);}
    std::queue<int>q;
    int d[M];
    int bfs(){
        memset(d,-1,sizeof(d));
        d[S]=0; q.push(S);
        while(!q.empty()){
            int x=q.front(); q.pop();
            for(int i=first[x];i;i=e[i].next){
                int now=e[i].to;
                if(d[now]==-1&&e[i].flow) d[now]=d[x]+1,q.push(now);
            }
        }
        return d[T]!=-1;
    }
    int dfs(int x,int a){
        if(x==T||a==0) return a;
        int flow=0,f;
        for(int& i=cur[x];i;i=e[i].next){
            int now=e[i].to;
            if(d[now]==d[x]+1&&(f=dfs(now,std::min(e[i].flow,a)))>0){
                e[i].flow-=f; e[i^1].flow+=f;
                flow+=f; 
                a-=f; if(!a) break;
            }
        }
        return flow;
    }
    int main(){
        int x,y;
        n=read(); m=read(); h=read();
        S=0; T=2*n+1;
        insert(S,1,inf); insert(1,1+n,inf);
        for(int i=1;i<=m;i++){
            x=read(); y=read();
            if(x==y) continue;
            insert(x+n,y,inf); insert(y+n,x,inf);
        }
        for(int i=1;i<=h;i++){
            x=read(); mark[x]=1;
            insert(x,x+n,inf);
            insert(x+n,T,inf);
        }
        for(int i=2;i<=n;i++) if(!mark[i]) insert(i,i+n,1);
        while(bfs()){for(int i=S;i<=T;i++) cur[i]=first[i]; ans+=dfs(S,inf);}
        printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj 1704: [Usaco2007 Mar]Face The Right Way 自动转身机——O(n)枚举O(n)计算就可以了

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    const int M=1e4+7;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,f[M],s[M],ansm,ansk=1;
    char ch[5];
    bool flag;
    int main(){
        n=read();
        for(int i=1;i<=n;i++){
            scanf("%s",ch);
            if(ch[0]=='B') s[i]=1,ansm++;
        }
        for(int k=1;k<=n;k++){
            flag=false;
            int sum=0,now=0;
            for(int i=1;i<=n-k+1;i++){
                if(f[i]==k) now^=1;
                if(s[i]^now) sum++,now^=1,f[i+k]=k;    
            }
            for(int i=n-k+2;i<=n;i++){
                if(f[i]==k) now^=1;
                if(s[i]^now){flag=true; break;}
            }
            if(flag) continue;
            if(sum<ansm) ansm=sum,ansk=k;
        }
        printf("%d %d
    ",ansk,ansm);
        return 0;
    }
    View Code

     bzoj 2199: [Usaco2011 Jan]奶牛议会——2—SAT

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using std::min;
    const int M=1e4+7;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int qread(){
        int x=read(),c=getchar();
        while(c!='Y'&&c!='N') c=getchar();
        if(c=='Y') return x<<1^1;
        return x<<1;
    }
    int n,m;
    int first[M],cnt,star[M],sum;
    struct node{int from,to,next;}e[2*M],q[2*M];
    void ins(int a,int b){e[++cnt]=(node){a,b,first[a]}; first[a]=cnt;}
    void qins(int a,int b){q[++sum]=(node){a,b,star[a]}; star[a]=sum;}
    int qc,color[M],dfn[M],low[M],stk[M],last[M],top,tot;
    void tarjan(int x){
        dfn[x]=low[x]=++tot;
        stk[++top]=x; last[x]=top; 
        for(int i=first[x];i;i=e[i].next){
            int now=e[i].to;
            if(!dfn[now]) tarjan(now),low[x]=min(low[x],low[now]);
            else if(!color[now]) low[x]=min(low[x],dfn[now]);
        }
        if(low[x]==dfn[x]){
            qc++;
            while(top>=last[x]) color[stk[top]]=qc,top--;
        }
    }
    int h,vis[M];
    void dfs(int x){
        vis[x]=h;
        for(int i=star[x];i;i=q[i].next){
            int now=q[i].to;
            if(vis[now]!=h) dfs(now);
        }
    }
    int pd(int x){
        h++; dfs(x);
        for(int i=1;i<=n;i++)if(vis[color[i<<1]]==h&&vis[color[i<<1^1]]==h) return 0;
        return 1;
    }
    char ans[M];
    int main(){
        int x,y;
        n=read(); m=read();
        for(int i=1;i<=m;i++){
            x=qread(); y=qread();
            ins(x^1,y); ins(y^1,x);
        }
        for(int i=2;i<=(n<<1^1);i++)if(!dfn[i]) tarjan(i);
        for(int i=1;i<=cnt;i++)if(color[e[i].from]!=color[e[i].to]) qins(color[e[i].from],color[e[i].to]);
        for(int i=1;i<=n;i++){
            if(color[i<<1]==color[i<<1^1]) return puts("IMPOSSIBLE"),0;
            int p=pd(color[i<<1]),q=pd(color[i<<1^1]);
            if(!p&&!q) return puts("IMPOSSIBLE"),0;
            if(p&&q) ans[i]='?';
            else if(p) ans[i]='N';
            else if(q) ans[i]='Y';
        }
        for(int i=1;i<=n;i++) printf("%c",ans[i]);
        return 0;
    }
    View Code

     bzoj 1702: [Usaco2007 Mar]Gold Balanced Lineup 平衡的队列——hash+map

    这道题 转2进制后求前缀和,前缀和的每位都减去第一位,如果有两个前缀和 i 和 j 相同的话,那么i+1~j这一段的k种颜色出现次数一样多

    这道题有单独的题解QAQ

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<map>
    #define LL unsigned long long
    const int M=2e5+7,P=233;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,k,ans;
    int d[M][35];
    std::map<LL,int>q;
    int find(int x){
        LL sum=0;
        for(int i=2;i<=k;i++) sum=sum*P+1LL*d[x][i];
        if(!q[sum]&&sum) q[sum]=x;
        return q[sum];
    }
    int main(){
        n=read(); k=read();
        for(int i=1;i<=n;i++){
            int now=0,x=read();
            for(;x;x>>=1) d[i][++now]=x&1;
            for(int j=1;j<=k;j++) d[i][j]+=d[i-1][j];
        }
        for(int i=1;i<=n;i++){
            for(int j=2;j<=k;j++) d[i][j]-=d[i][1];
            ans=std::max(ans,i-find(i));
        }printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj 1718: [Usaco2006 Jan] Redundant Paths 分离的路径——边双连通分量缩点求出叶子数

    #include<cstdio>
    #include<cstring>
    #include<cstring>
    #include<algorithm>
    using std::min;
    const int M=1e4+7;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,f[5*M];
    int dfn[M],low[M],last[M],stk[M],top;
    int color[M],hc,T;
    int first[M],cnt=1,star[M],sum=1;
    struct node{int from,to,next;}e[5*M],q[5*M];
    void ins(int a,int b){e[++cnt]=(node){a,b,first[a]}; first[a]=cnt;}
    void insert(int a,int b){ins(a,b); ins(b,a);}
    void insq(int a,int b){q[++sum]=(node){a,b,star[a]}; star[a]=sum;}
    void insertq(int a,int b){insq(a,b); insq(b,a);}
    void tarjan(int x){
        low[x]=dfn[x]=++T;
        stk[++top]=x; last[x]=top;
        for(int i=first[x];i;i=e[i].next){
            int now=e[i].to;
            if(f[i^1]) continue; f[i]=1;
            if(!dfn[now]) tarjan(now),low[x]=min(low[x],low[now]);
            else if(!color[now]) low[x]=min(low[x],dfn[now]);
        }
        if(low[x]==dfn[x]) for(hc++;top>=last[x];top--) color[stk[top]]=hc;
    }
    int in[M],vis[M],ans;
    int main(){
        int x,y;
        n=read(); m=read();
        for(int i=1;i<=m;i++) x=read(),y=read(),insert(x,y);
        for(int i=1;i<=n;i++) if(!dfn[i]) tarjan(i);
        for(int i=2;i<=cnt;i+=2) 
        if(color[e[i].from]!=color[e[i].to]) in[color[e[i].from]]++,in[color[e[i].to]]++;
        for(int i=1;i<=hc;i++) if(in[i]==1) ans++;
        printf("%d
    ",(ans+1)>>1);
        return 0;
    }
    View Code

     bzoj 1700: [Usaco2007 Jan]Problem Solving 解题——dp

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using std::min;
    const int M=557,inf=0x3f3f3f3f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int ans=inf,n,m,f[M][M];
    int k,s1[M],s2[M];
    int main(){
        memset(f,0x3f,sizeof(f));
        n=read(); m=read();
        for(int i=1;i<=m;i++){
            k=read(); s1[i]=s1[i-1]+k;
            k=read(); s2[i]=s2[i-1]+k;
        }
        f[0][0]=0;f[1][1]=1;f[1][0]=2;
        for(int k=2;k<=m;k++){
            for(int i=1;i<=k;i++)if(s1[k]-s1[k-i]<=n)
            for(int j=0;j<=k-i;j++)if((s1[k]-s1[k-i])+(s2[k-i]-s2[k-i-j])<=n)
            f[k][i]=std::min(f[k][i],f[k-i][j]+1);
            for(int i=1;i<=m;i++)if(s2[k]-s2[k-i]<=n)f[k][0]=min(f[k][0],f[k][i]+1);
        }
        ans=f[m][0]+1;
        for(int i=1;i<=m;i++) if(s2[m]-s2[m-i]<=n) ans=min(ans,f[m][i]+2);
        printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj 1776: [Usaco2010 Hol]cowpol 奶牛政坛——树的直径QAQ

    可以证明一个结论 一棵树的直径必然存在一条过深度最深的点

    所以我们可以求出每种颜色最深的点 然后其他点和他求一波lca算答案就可以了

    这样的复杂度是nlogn的 

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    const int M=3e5+7;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int rt,n,k,c[M],mx[M],id[M];
    int first[M],cnt;
    struct node{int to,next;}e[M];
    int f[M][32],fa[M],dep[M];
    void ins(int a,int b){e[++cnt]=(node){b,first[a]}; first[a]=cnt;}
    void dfs(int x){//printf("[%d]
    ",x);
        for(int i=1;(1<<i)<=dep[x];i++) f[x][i]=f[f[x][i-1]][i-1];
        for(int i=first[x];i;i=e[i].next){
            int now=e[i].to;
            dep[now]=dep[x]+1;
            f[now][0]=x;
            if(dep[now]>mx[c[now]]) mx[c[now]]=dep[now],id[c[now]]=now;
            dfs(now);
        }
    }
    int find(int x,int y){
        if(dep[x]<dep[y]) std::swap(x,y);
        int d=dep[x]-dep[y];
        for(int i=0;(1<<i)<=d;i++) if((1<<i)&d) x=f[x][i];
        if(x==y) return x;
        for(int i=30;i>=0;i--)
         if((1<<i)<=dep[x]&&f[x][i]!=f[y][i]) x=f[x][i],y=f[y][i];
        return f[x][0];
    }
    int ans[M];
    int main(){
        int x,y;
        n=read(); k=read();
        for(int i=1;i<=n;i++){
            c[i]=read(); fa[i]=read();
            if(fa[i]) ins(fa[i],i);
            else rt=i;
        }
        dep[rt]=1; dfs(rt);
        for(int i=1;i<=n;i++){
            int lca=find(i,id[c[i]]);
            ans[c[i]]=std::max(ans[c[i]],dep[i]+dep[id[c[i]]]-2*dep[lca]);
        }
        for(int i=1;i<=k;i++) printf("%d
    ",ans[i]);
        return 0;
    }
    View Code

     bzoj 1778: [Usaco2010 Hol]Dotp 驱逐猪猡——高斯消元+概率dp(待填QAQ

    bzoj 3126: [Usaco2013 Open]Photo——单调队列优化dp

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using std::min;
    using std::max;
    const int M=250007,inf=0x3f3f3f3f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,x,y;
    int l[M],r[M],f[M];
    int q[M],ql=1,qr;
    int main(){
        n=read(); m=read();
        for(int i=1;i<=n+1;i++) r[i]=i-1;
        for(int i=1;i<=m;i++){
            x=read(); y=read();
            r[y]=min(r[y],x-1);
            l[y+1]=max(l[y+1],x);
        }
        for(int i=n;i;i--) r[i]=min(r[i],r[i+1]);
        for(int i=2;i<=n+1;i++) l[i]=max(l[i],l[i-1]);
        f[qr=1]=0;
        for(int i=1;i<=n+1;i++){
            for(int k=r[i-1]+1;k<=r[i];k++){
                while(ql<=qr&&f[q[qr]]<=f[k]) qr--;
                q[++qr]=k;
            }
            while(ql<=qr&&q[ql]<l[i]) ql++;
            if(ql>qr) f[i]=-inf;
            else f[i]=f[q[ql]]+1;
        }
        if(f[n+1]>=0) printf("%d
    ",f[n+1]-1);
        else printf("-1
    ");
        return 0;
    }
    View Code

     当然这道题也有差分约束的写法QAQ——其实是硬水过去的QAQ

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    using std::queue;
    const int M=250007,inf=0x3f3f3f3f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    bool f=false;
    int ans,n,m;
    int first[M],cnt;
    struct node{int to,next,w;}e[5*M];
    void ins(int a,int b,int w){e[++cnt]=(node){b,first[a],w}; first[a]=cnt;}
    int dis[M],vis[M];
    struct pos{int dis,id;};
    bool operator <(pos a,pos b){return a.dis>b.dis;};
    std::priority_queue<pos>q;
    void spfa(){
        memset(dis,0x3f,sizeof(dis));
        q.push((pos){0,0});
        dis[0]=0; vis[0]=1;
        while(!q.empty()){
            pos x=q.top(); q.pop();
            for(int i=first[x.id];i;i=e[i].next){
                int now=e[i].to;
                if(dis[now]>dis[x.id]+e[i].w){
                    ans++; if(ans>300000) return void(f=true);
                    dis[now]=dis[x.id]+e[i].w;
                    if(!vis[now]) vis[now]=1,q.push((pos){dis[now],now});
                }
            }
            vis[x.id]=0;
        }
    }
    int main(){
        int l,r;
        n=read(); m=read();
        for(int i=1;i<=m;i++) l=read(),r=read(),ins(l-1,r,1),ins(r,l-1,-1);
        for(int i=1;i<=n;i++) ins(i-1,i,1),ins(i,i-1,0);
        spfa();
        if(f) printf("-1
    ");
        else printf("%d
    ",dis[n]);
        return 0;
    }
    View Code

    bzoj 1731: [Usaco2005 dec]Layout 排队布局——差分约束

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<cmath>
    #include<queue>
    #define LL long long
    const int M=1e3+7,N=1e5+7,inf=0x3f3f3f3f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,ml,md,h[M],vis[M];
    int x,y,w,dis[M];
    int first[M],cnt;
    struct node{int to,next,w;}e[N];
    void ins(int a,int b,int w){e[++cnt]=(node){b,first[a],w}; first[a]=cnt;}
    std::queue<int>q;
    bool f=false;
    void spfa(){
        memset(dis,0x3f,sizeof(dis));
        q.push(1); dis[1]=0; 
        vis[1]=1; h[1]=1;
        while(!q.empty()){
            int x=q.front(); q.pop(); 
            for(int i=first[x];i;i=e[i].next){
                int now=e[i].to;
                if(dis[now]>dis[x]+e[i].w){
                    dis[now]=dis[x]+e[i].w;
                    if(!vis[now]){
                        vis[now]=1; q.push(now);
                        h[now]++; if(h[now]==n){f=true; return ;}
                    }
                }
            }
            vis[x]=0;
        }
    }
    int main(){
        n=read(); ml=read(); md=read();
        for(int i=1;i<=ml;i++) x=read(),y=read(),w=read(),ins(x,y,w);
        for(int i=1;i<=md;i++) x=read(),y=read(),w=read(),ins(y,x,-w);
        for(int i=1;i<n;i++) ins(i+1,i,0);
        spfa();
        if(f) printf("-1
    ");
        else if(dis[n]==inf) printf("-2
    ");
        else printf("%d
    ",dis[n]);
        return 0;
    }
    View Code

     bzoj 1705: [Usaco2007 Nov]Telephone Wire 架设电话线——dp

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using std::min;
    using std::max;
    const int M=1e5+7,inf=0x3f3f3f3f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,c,ans,mn;
    int h[M],f[M][107];
    int main(){
        n=read(); c=read();
        for(int i=1;i<=n;i++) h[i]=read();
        memset(f,0x3f,sizeof(f));
        for(int i=h[1];i<=100;i++) f[1][i]=(h[1]-i)*(h[1]-i);
        for(int k=2;k<=n;k++){
            mn=inf;
            for(int i=h[k-1];i<max(h[k-1],h[k]);i++) mn=min(mn,f[k-1][i]-c*i);
            for(int i=h[k];i<=100;i++){
                mn=min(mn,f[k-1][i]-c*i);
                f[k][i]=mn+c*i+(h[k]-i)*(h[k]-i);
            }
            mn=inf;
            for(int i=100;i>=h[k];i--){
                if(i>=h[k-1]) mn=min(mn,f[k-1][i]+c*i);
                f[k][i]=min(f[k][i],mn-c*i+(h[k]-i)*(h[k]-i));
            }
        }
        ans=inf;
        for(int i=1;i<=100;i++) ans=min(ans,f[n][i]);
        printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj 1755: [Usaco2005 qua]Bank Interest-.....

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    double R,M;
    int y;
    int main(){
        scanf("%lf %lf %d",&R,&M,&y);
        for(int i=1;i<=y;i++) M=M*(1+R/100);
        printf("%d
    ",(int)M);
        return 0;
    }
    View Code

     bzoj 2200: [Usaco2011 Jan]道路和航线

    1——spfa+SLF优化QAQ

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    const int M=3e4+7,inf=0x3f3f3f3f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    bool f=false;
    int n,nr,np,S;
    int first[M],cnt;
    struct node{int to,next,w;}e[7*M];
    void ins(int a,int b,int w){e[++cnt]=(node){b,first[a],w}; first[a]=cnt;}
    void insert(int a,int b,int w){ins(a,b,w); ins(b,a,w);}
    int dis[M],vis[M];
    int q[M],head,tail=1;
    void spfa(){
        memset(dis,0x3f,sizeof(dis));
        dis[S]=0; vis[S]=1;
        q[head]=S;
        while(head!=tail){
            int x=q[head++]; if(head>M) head=0;
            for(int i=first[x];i;i=e[i].next){
                int now=e[i].to;
                if(dis[now]>dis[x]+e[i].w){
                    dis[now]=dis[x]+e[i].w;
                    if(!vis[now]){
                        vis[now]=1;
                        if(dis[now]<=dis[q[head]]){
                            head--;
                            if(head<0) head=M;
                            q[head]=now;
                        }
                        else{q[tail++]=now; if(tail>M) tail=0;}
                    }
                }
            }
            vis[x]=0;
        }
        for(int i=1;i<=n;i++) 
            if(dis[i]>=inf) printf("NO PATH
    ");
            else printf("%d
    ",dis[i]);
    }
    int main(){
        int x,y,w;
        n=read(); nr=read(); np=read(); S=read();
        for(int i=1;i<=nr;i++) x=read(),y=read(),w=read(),insert(x,y,w);
        for(int i=1;i<=np;i++) x=read(),y=read(),w=read(),ins(x,y,w);
        spfa();
        return 0;
    }
    View Code

     2——dfs染色+拓扑+dijkstra

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    const int M=3e4+7,inf=0x3f3f3f3f;
    char buf[88*M],*ptr=buf-1;
    int read(){
        int ans=0,f=1,c=*++ptr;
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=*++ptr;}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=*++ptr;}
        return ans*f;
    }
    bool flag=false;
    int n,nr,np,S;
    int first[M],cnt;
    struct node{int to,next,w;}e[5*M];
    void ins(int a,int b,int w){e[++cnt]=(node){b,first[a],w}; first[a]=cnt;}
    void insert(int a,int b,int w){ins(a,b,w); ins(b,a,w);}
    int color[M],hc;
    void dfs(int x){
        color[x]=hc;
        for(int i=first[x];i;i=e[i].next){
            int now=e[i].to;
            if(!color[now]) dfs(now);
        }
    }
    int sum,star[M];
    struct pos{int from,to,next,w;}q[5*M];
    void insq(int a,int b,int w){q[++sum]=(pos){a,b,star[a],w}; star[a]=sum;}
    int f[M],vis[M];
    void find(int x){
        vis[x]=f[color[x]]=n+1;
        for(int i=first[x];i;i=e[i].next){
            int now=e[i].to;
            if(!vis[now]) find(now);
        }
    }
    int k,dis[M],wh[M],mark[5*M];
    struct QAQ{
        int d,id;
        bool operator <(const QAQ& x)const{return x.d<d;}
    };
    std::priority_queue<QAQ>qu[M];
    std::queue<int>Q;
    int in[M];
    void find_w(int x){
        vis[x]=k;
        for(int i=star[x];i;i=q[i].next){
            int now=color[q[i].to];
            dis[q[i].to]=std::min(dis[q[i].to],dis[x]+q[i].w);
            qu[now].push((QAQ){dis[q[i].to],q[i].to});
            if(!--in[now]) Q.push(now);
        }
        for(int i=first[x];i;i=e[i].next)if(!mark[i]){
            int now=e[i].to;
            if(vis[now]!=k) find_w(now);
        }
    }
    int main(){
        fread(buf,1,sizeof(buf),stdin);
        int x,y,w;
        n=read(); nr=read(); np=read(); S=read();
        for(int i=1;i<=nr;i++) x=read(),y=read(),w=read(),insert(x,y,w);
        for(int i=1;i<=n;i++)if(!color[i]) hc++,wh[hc]=i,dfs(i);
        for(int i=1;i<=np;i++) x=read(),y=read(),w=read(),ins(x,y,w),mark[cnt]=1,insq(x,y,w);
        memset(dis,0x3f,sizeof(dis)); dis[S]=0;
        for(int i=1;i<=sum;i++) if(f[color[q[i].from]]&&f[color[q[i].to]]) in[color[q[i].to]]++;
        Q.push(color[S]); qu[color[S]].push((QAQ){0,S});
        while(!Q.empty()){
            int x=Q.front(); Q.pop(); k++;
            while(!qu[x].empty()){
                QAQ p=qu[x].top(); qu[x].pop();
                if(dis[p.id]<p.d) continue;
                for(int i=first[p.id];i;i=e[i].next)if(!mark[i]){
                    int now=e[i].to; 
                    if(dis[now]>dis[p.id]+e[i].w) dis[now]=dis[p.id]+e[i].w,qu[x].push((QAQ){dis[now],now});
                }
            }
            find_w(wh[x]);
        }
        for(int i=1;i<=n;i++) 
            if(dis[i]>=inf) printf("NO PATH
    ");
            else printf("%d
    ",dis[i]);
        return 0;
    }
    View Code

     bzoj 1774: [Usaco2009 Dec]Toll 过路费——(改)floyd

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using std::min;
    using std::max;
    const int M=357;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,k,map[M][M],h[M],ans[M][M];
    struct node{int id,h;}q[M];
    bool cmp(node a,node b){return a.h<b.h;}
    void floyd(){
        memset(ans,0x3f,sizeof(ans));
        std::sort(q+1,q+1+n,cmp);
        for(int k=1;k<=n;k++)
        for(int i=1;i<=n;i++)
        for(int j=1;j<=n;j++){
              map[i][j]=min(map[i][j],map[i][q[k].id]+map[q[k].id][j]);
              ans[i][j]=min(ans[i][j],map[i][j]+max(max(h[i],h[j]),q[k].h));
        }
    }
    int main(){
        int x,y,w;
        n=read(); m=read(); k=read();
        memset(map,0x3f,sizeof(map));
        for(int i=1;i<=n;i++) h[i]=q[i].h=read(),q[i].id=i;
        for(int i=1;i<=m;i++) x=read(),y=read(),w=read(),map[x][y]=map[y][x]=min(map[x][y],w);
        floyd();
        for(int i=1;i<=k;i++) x=read(),y=read(),printf("%d
    ",ans[x][y]);
        return 0;
    }
    View Code

     bzoj 1575: [Usaco2009 Jan]气象牛Baric——dp

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<cmath>
    using std::min;
    const int M=107,inf=0x3f3f3f3f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,k,f[M][M];
    int v[M],star[M],mid[M][M],last[M];
    int main(){
        n=read(); k=read();
        for(int i=1;i<=n;i++) v[i]=read();
        for(int i=1;i<=n;i++){
            for(int j=1;j<i;j++) star[i]+=2*abs(v[i]-v[j]);
            for(int j=i+1;j<=n;j++) last[i]+=2*abs(v[i]-v[j]);
            for(int j=i+1;j<=n;j++) for(int k=i+1;k<j;k++) mid[i][j]+=abs(2*v[k]-v[i]-v[j]);
        }
        memset(f,0x3f,sizeof(f));
        for(int i=1;i<=n;i++){
            f[i][1]=star[i];
            for(int j=2;j<=i;j++)
            for(int k=j-1;k<i;k++) f[i][j]=min(f[i][j],f[k][j-1]+mid[k][i]);
        }
        int ansh=inf,ans=inf;
        for(int i=1;i<=n;i++)
            for(int j=1;j<=i;j++)
            if(f[i][j]+last[i]<=k){
                if(ansh>j) ansh=j,ans=f[i][j]+last[i];
                else if(j==ansh) ans=min(ans,f[i][j]+last[i]);
            }
        printf("%d %d
    ",ansh,ans);
        return 0;
    }
    View Code

     bzoj 1783: [Usaco2010 Jan]Taking Turns——博弈dp

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #define LL long long
    const int M=750007;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,id;
    LL f[M],g[M],v[M];
    int main(){
        n=read(); id=n+1;
        for(int i=1;i<=n;i++) v[i]=read();
        for(int i=n;i>=1;i--){
            f[i]=g[id]+v[i];
            g[i]=f[id];
            if(f[i]>=f[id]) id=i;
        }
        printf("%lld %lld
    ",f[id],g[id]);
        return 0;
    }
    View Code

     bzoj 1577: [Usaco2009 Feb]庙会捷运Fair Shuttle——大根堆+小根堆+贪心

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<vector>
    #include<queue>
    const int M=3e4+7;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int f[2*M],cnt,cost,k,n,c,ans;
    struct pos{
        int id,h,ed;
        bool operator <(const pos &x)const{return x.ed<ed;}
    };
    std::vector<pos>e[M];
    std::priority_queue<pos>q1;
    struct Q{
        int id,h,ed;
        bool operator <(const Q &x)const{return x.ed>ed;}
    };
    std::priority_queue<Q>q2;
    int main(){
        int v,x,y;
        k=read(); n=read(); c=read();
        for(int i=1;i<=k;i++) x=read(),y=read(),v=read(),e[x].push_back((pos){++cnt,v,y});
        for(int i=1;i<=n;i++){
            while(!q1.empty()){
                pos x=q1.top(); 
                if(x.ed>i) break;
                q1.pop();
                if(f[x.id]) continue;
                f[x.id]=1; cost-=x.h; ans+=x.h; 
            }
            int mx=e[i].size();
            for(int j=0;j<mx;j++){
                q1.push((pos){e[i][j].id,e[i][j].h,e[i][j].ed});
                q2.push((Q){e[i][j].id,e[i][j].h,e[i][j].ed});
                cost+=e[i][j].h;
            }
            while(cost>c){
                Q x=q2.top(); q2.pop();
                if(f[x.id]) continue;
                f[x.id]=1;
                if(cost-c>=x.h){cost-=x.h; continue;}
                int now=cost-c;
                cnt++;
                q1.push((pos){cnt,x.h-now,x.ed});
                q2.push((Q){cnt,x.h-now,x.ed});
                cost=c;
            }
        }
        printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj 1914: [Usaco2010 OPen]Triangle Counting 数三角形——极角排序

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #define LL long long
    using std::sort;
    const int M=2e5+7,inf=0x3f3f3f3f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n;
    struct pos{int x,y,wh; double k;}q[M];
    bool cmp(pos a,pos b){return a.wh!=b.wh?a.wh<b.wh:a.k>b.k;}
    int main(){
        int x,y;
        n=read();
        for(int i=1;i<=n;i++){
            x=read(); y=read();
            q[i].x=x; q[i].y=y;
            if(x) q[i].k=1.0*y/x; else q[i].k=-inf;
            if(x>0&&y>=0) q[i].wh=1;
            else if(x>=0&&y<0) q[i].wh=2;
            else if(x<0&&y<=0) q[i].wh=3;
            else q[i].wh=4;
        }
        LL ans=1LL*n*(n-1)*(n-2)/6;
        sort(q+1,q+1+n,cmp);
        LL sum=1,ly=2;
        for(int i=1;i<=n;i++){
            sum--;
            while(1LL*q[ly].y*q[i].x<1LL*q[i].y*q[ly].x){
                ly++; sum++;
                if(ly>n) ly-=n;
            }
            ans=ans-sum*(sum-1)/2;
        }
        printf("%lld
    ",ans);
        return 0;
    }
    View Code

     bzoj 1696: [Usaco2007 Feb]Building A New Barn新牛舍——中位数排序

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<cmath>
    #include<map>
    using std::sort;
    using std::min;
    const int M=2e4+7;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int ans,sum,n,x[M],y[M];
    struct pos{
        int x,y;
        bool operator <(const pos& h)const{return h.x!=x?h.x<x:h.y<y;}
    }q[M];
    std::map<pos,bool>vis;
    int main(){
        n=read();
        for(int i=1;i<=n;i++){
            x[i]=read(); y[i]=read();
            q[i].x=x[i]; q[i].y=y[i];
        }
        sort(x+1,x+1+n); sort(y+1,y+1+n);
        int x1=x[(n+1)/2],y1=y[(n+2)/2],x2=x[(n+2)/2],y2=y[(n+1)/2];
        if(x1==x2&&y1==y2){
            bool f=false;
            for(int i=1;i<=n;i++)if(q[i].x==x1&&q[i].y==y1){f=true; break;}
            if(!f){
                ans=1;
                for(int i=1;i<=n;i++){
                    sum=sum+abs(q[i].x-x1);
                    sum=sum+abs(q[i].y-y1);
                }
            }
            else{
                int nx=x1,ny=y1-1;
                for(int i=1;i<=n;i++){
                    sum=sum+abs(q[i].x-nx);
                    sum=sum+abs(q[i].y-ny);
                }
                ans=1; nx=x1; ny=y1+1;
                int now=0;
                for(int i=1;i<=n;i++){
                    now=now+abs(q[i].x-nx);
                    now=now+abs(q[i].y-ny);
                }
                if(sum>now) ans=1;
                if(sum==now) ans++;
                nx=x1+1; ny=y1;
                now=0;
                for(int i=1;i<=n;i++){
                    now=now+abs(q[i].x-nx);
                    now=now+abs(q[i].y-ny);
                }
                if(sum>now) ans=1;
                if(sum==now) ans++;
                now=0;
                nx=x1-1; ny=y1;
                for(int i=1;i<=n;i++){
                    now=now+abs(q[i].x-nx);
                    now=now+abs(q[i].y-ny);
                }
                if(sum>now) ans=1;
                if(sum==now) ans++;
            }
            printf("%d %d
    ",sum,ans);
        }
        else{
            ans=(x2-x1+1)*(y1-y2+1);
            for(int i=1;i<=n;i++){
                if(q[i].x>=x1&&q[i].x<=x2&&q[i].y>=y2&&q[i].y<=y1){
                    if(!vis[(pos){q[i].x,q[i].y}]){ans--; vis[(pos){q[i].x,q[i].y}]=1;}
                }
                sum=sum+abs(q[i].x-x1);
                sum=sum+abs(q[i].y-y1);
            }
            printf("%d %d
    ",sum,ans);
        }
        return 0;
    }
    View Code

     bzoj 1590: [Usaco2008 Dec]Secret Message 秘密信息

    1. 排序版本 如果A是B的前缀 那么字典序 A<=B<=Ainf  正反做一次就可以了 就是有点慢=_=

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<vector>
    using std::sort;
    using std::lower_bound;
    using std::upper_bound;
    const int M=50007,inf=0x3f3f3f3f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,k;
    int ans[M],f[M];
    struct pos{
        int id; std::vector<int>s;
        bool operator <(const pos& x)const{return s<x.s;}
    }s1[M],s2[M];
    int main(){
        n=read(); m=read();
        for(int i=1;i<=n;i++){
            k=read();
            for(int j=1;j<=k;j++) s1[i].s.push_back(read()),s1[i].id=i;
        }
        for(int i=1;i<=m;i++){
            k=read();
            for(int j=1;j<=k;j++)  s2[i].s.push_back(read()),s2[i].id=i;
        }
        sort(s1+1,s1+1+n); sort(s2+1,s2+1+m);
        for(int i=1;i<=n;i++){
            int lx=lower_bound(s2+1,s2+1+m,s1[i])-s2;
            s1[i].s.push_back(inf);
            int rx=upper_bound(s2+1,s2+1+m,s1[i])-s2;
            s1[i].s.pop_back();
            f[lx]++; f[rx]--;
        }
        for(int i=1;i<=m;i++){
            int lx=upper_bound(s1+1,s1+1+n,s2[i])-s1;
            s2[i].s.push_back(inf);
            int rx=upper_bound(s1+1,s1+1+n,s2[i])-s1;
            s2[i].s.pop_back();
            ans[s2[i].id]=rx-lx;
        }
        int now=0;
        for(int i=1;i<=m;i++){now+=f[i]; ans[s2[i].id]+=now;}
        for(int i=1;i<=m;i++) printf("%d
    ",ans[i]);
        return 0;
    }
    View Code

     2. trie版本 记一下每个位置作为多少个串的前缀 以及每个串的终止位置 统计一波就可以了 很快QAQ

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    const int M=1e6+7;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,k,son[M],sum[M],ans[M];
    int s[M],c[M][2],cnt;
    void insert(int len){
        int rt=0;
        for(int i=1;i<=len;i++){
            if(!c[rt][s[i]]) c[rt][s[i]]=++cnt;
            rt=c[rt][s[i]];
            son[rt]++;
        }
        sum[rt]++;
    }
    int find(int len){
        int rt=0,ans=0;
        for(int i=1;i<=len;i++){
            if(!c[rt][s[i]]) break;
            rt=c[rt][s[i]];
            if(i==len) ans+=son[rt];
            else ans+=sum[rt];
        }
        return ans;
    }
    int main(){
        n=read(); m=read();
        for(int i=1;i<=n;i++){
            k=read();
            for(int j=1;j<=k;j++) s[j]=read();
            insert(k);
        }
        for(int i=1;i<=m;i++){
            k=read();
            for(int j=1;j<=k;j++) s[j]=read();
            printf("%d
    ",find(k));
        }
        return 0;
    }
    View Code

     bzoj 3940: [Usaco2015 Feb]Censoring——another坑QAQ

    bzoj 2097: [Usaco2010 Dec]Exercise 奶牛健美操——二分+树形dp+贪心

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using std::sort;
    const int M=2e5+7;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,k,sz[M];
    int first[M],cnt,s[M];
    struct node{int to,next;}e[2*M];
    void ins(int a,int b){e[++cnt]=(node){b,first[a]}; first[a]=cnt;}
    void insert(int a,int b){ins(a,b); ins(b,a);}
    bool cmp(int x,int y){return x>y;}
    int ans,mx;
    void dfs(int x,int fa){
        sz[x]=0;
        for(int i=first[x];i;i=e[i].next){
            int now=e[i].to;
            if(now==fa) continue;
            dfs(now,x);
        }
        cnt=0;
        for(int i=first[x];i;i=e[i].next){
            int now=e[i].to;
            if(now==fa) continue;
            s[++cnt]=sz[now]+1;
        }
        sort(s+1,s+1+cnt,cmp);
        int k=1; 
        s[cnt+1]=s[cnt+2]=s[cnt+3]=0;
        while(s[k]+s[k+1]>mx) ans++,k++;
        sz[x]=s[k];
    }
    bool check(int ly){
        mx=ly; ans=0;
        dfs(1,-1);
        return ans<=k;
    }
    int main(){
        int x,y;
        n=read(); k=read();
        for(int i=1;i<n;i++) x=read(),y=read(),insert(x,y);
        int l=1,r=n;
        while(l<r){
            int mid=(l+r)>>1;
            if(check(mid)) r=mid;
            else l=mid+1;
        }printf("%d
    ",l);
        return 0;
    }
    View Code

     bzoj 1693: [Usaco2007 Demo]Asteroids——二分图匹配

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    using std::min;
    const int M=2e3+7,inf=0x3f3f3f3f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,k,cur[M],d[M];
    int S,T,ans;
    int first[M],cnt=1;
    struct node{int to,next,flow;}e[20*M];
    void ins(int a,int b,int flow){e[++cnt]=(node){b,first[a],flow}; first[a]=cnt;}
    void insert(int a,int b,int flow){ins(a,b,flow); ins(b,a,0);}
    std::queue<int>q;
    int bfs(){
        memset(d,-1,sizeof(d));
        d[S]=1; q.push(S);
        while(!q.empty()){
            int x=q.front(); q.pop();
            for(int i=first[x];i;i=e[i].next){
                int now=e[i].to;
                if(e[i].flow&&d[now]==-1) d[now]=d[x]+1,q.push(now); 
            }
        }
        return d[T]!=-1;
    }
    int dfs(int x,int a){
        if(x==T||a==0) return a;
        int flow=0,f;
        for(int& i=cur[x];i;i=e[i].next){
            int now=e[i].to;
            if(d[now]==d[x]+1&&(f=dfs(now,min(e[i].flow,a)))>0){
                e[i].flow-=f; e[i^1].flow+=f;
                flow+=f;
                a-=f; if(!a) break;
            }
        }
        return flow;
    }
    int main(){
        int x,y;
        n=read(); k=read();
        S=0; T=2*n+1;
        for(int i=1;i<=n;i++) insert(S,i,1);
        for(int i=1;i<=n;i++) insert(i+n,T,1);
        for(int i=1;i<=k;i++) x=read(),y=read(),insert(x,y+n,1);
        while(bfs()){for(int i=S;i<=T;i++) cur[i]=first[i]; ans+=dfs(S,inf);}
        printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj 1663: [Usaco2006 Open]赶集——dp

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using std::sort;
    using std::max;
    const int M=1e3+7,inf=0x3f3f3f3f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int ans,n,ly[M][M],f[M];
    struct pos{int h,id;}q[M];
    bool cmp(pos a,pos b){return a.h<b.h;}
    int main(){
        n=read();
        for(int i=1;i<=n;i++) q[i].h=read(),q[i].id=i;
        sort(q+1,q+1+n,cmp);
        for(int i=1;i<=n;i++) for(int j=1;j<=n;j++) ly[i][j]=read();
        for(int i=1;i<=n;i++){
            if(ly[1][q[i].id]<=q[i].h) f[i]=1;
            else f[i]=-inf;
            for(int j=1;j<i;j++)
            if(q[j].h+ly[q[j].id][q[i].id]<=q[i].h) f[i]=max(f[i],f[j]+1);
        }
        for(int i=1;i<=n;i++) ans=max(ans,f[i]); printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj 1742: [Usaco2005 nov]Grazing on the Run 边跑边吃草——一类dp问题QAQ

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using std::min;
    using std::sort;
    const int M=1e3+7;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,star;
    int f1[M][M],f2[M][M],s[M];
    int main(){
        n=read(); star=read();
        for(int i=1;i<=n;i++) s[i]=read();
        sort(s+1,s+1+n);
        for(int i=1;i<=n;i++) f1[i][i]=f2[i][i]=n*abs(star-s[i]);
        for(int len=2;len<=n;len++){
            for(int i=1;i<=n-len+1;i++){
                int j=i+len-1,now=n-j+i;
                f1[i][j]=min(f1[i+1][j]+(s[i+1]-s[i])*now,f2[i+1][j]+(s[j]-s[i])*now);
                f2[i][j]=min(f1[i][j-1]+(s[j]-s[i])*now,f2[i][j-1]+(s[j]-s[j-1])*now);
            }
        }printf("%d
    ",min(f1[1][n],f2[1][n]));
        return 0;
    }
    View Code

     bzoj 1594: [Usaco2008 Jan]猜数游戏——二分+线段树

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using std::sort;
    using std::max;
    using std::min;
    const int M=1e5+7,N=3e6+7;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int cnt,n,m,lx[M],rx[M],mn[N],sign[N],ll[M],rr[M];
    struct pos{int l,r,v;}q[M],s[M];
    bool cmp(pos a,pos b){return a.v>b.v;}
    void clear(){
        cnt=1;
        memset(mn,0,sizeof(mn));
        memset(sign,0,sizeof(sign));
    }
    int L,R;
    void up(int x){mn[x]=min(mn[x<<1],mn[x<<1^1]);}
    void down(int x){
        if(!sign[x]) return ;
        int ls=x<<1,rs=x<<1^1;
        sign[x]=0; sign[ls]=sign[rs]=1;
        mn[ls]=mn[rs]=1;
    }
    void modify(int x,int l,int r){
        if(L<=l&&r<=R){
            mn[x]=1; sign[x]=1;
            return ;
        }
        down(x);
        int mid=(l+r)>>1;
        if(L<=mid) modify(x<<1,l,mid);
        if(R>mid) modify(x<<1^1,mid+1,r);
        up(x);
    }
    int push_mn(int x,int l,int r){
        if(L<=l&&r<=R) return mn[x];
        down(x);
        int mid=(l+r)>>1,ans=1;
        if(L<=mid) ans=min(ans,push_mn(x<<1,l,mid));
        if(R>mid) ans=min(ans,push_mn(x<<1^1,mid+1,r));
        return ans;
    }
    bool check(int k){
        if(!k) return 1;
        clear(); 
        for(int i=1;i<=k;i++) s[i]=q[i];
        sort(s+1,s+1+k,cmp);
        int color=s[1].v; 
        lx[1]=s[1].l; rx[1]=s[1].r;
        ll[1]=lx[cnt],rr[1]=rx[cnt];
        for(int i=2;i<=k;i++){
            if(s[i].v!=color){
                cnt++; color=s[i].v;
                lx[cnt]=s[i].l; rx[cnt]=s[i].r;
                ll[cnt]=lx[cnt]; rr[cnt]=rx[cnt];
            }
            else lx[cnt]=min(lx[cnt],s[i].l),rx[cnt]=max(rx[cnt],s[i].r),ll[cnt]=max(ll[cnt],s[i].l),rr[cnt]=min(rr[cnt],s[i].r);
            if(ll[cnt]>rr[cnt]) return 1;
        }
        for(int i=1;i<=cnt;i++){
            L=ll[i]; R=rr[i];
            if(push_mn(1,1,n)!=0) return 1;
            L=lx[i]; R=rx[i];
            modify(1,1,n);
        }
        return 0;
    }
    int main(){
        n=read(); m=read();
        for(int i=1;i<=m;i++) q[i].l=read(),q[i].r=read(),q[i].v=read();
        int l=1,r=m+1;
        while(l<r){
            int mid=(l+r)>>1;
            if(check(mid)) r=mid;
            else l=mid+1;
        }
        if(r>m) printf("0
    ");
        else printf("%d
    ",r);
        return 0;
    }
    View Code

     bzoj 1583: [Usaco2009 Mar]Moon Mooing 哞哞叫

    因为两个函数都是单增的所以维护队列就可以了

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #define LL long long
    const int M=4e6+7;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    LL num[15][15],c,n;
    LL ans[M],cnt,l=1,r=1;
    int main(){
        c=read(); n=read();
        for(int i=1;i<=2;i++) for(int j=1;j<=3;j++) num[i][j]=read();
        ans[++cnt]=c;
        LL n1=c*num[1][1]/num[1][3]+num[1][2];
        LL n2=c*num[2][1]/num[2][3]+num[2][2];
        while(cnt<n){
            if(n1<n2){
                if(n1!=ans[cnt]) ans[++cnt]=n1;
                n1=ans[++l]*num[1][1]/num[1][3]+num[1][2];
            }
            else{
                if(n2!=ans[cnt]) ans[++cnt]=n2;
                n2=ans[++r]*num[2][1]/num[2][3]+num[2][2];
            }
        }printf("%lld
    ",ans[cnt]);
        return 0;
    }
    View Code

     bzoj 1716: [Usaco2006 Dec]The Fewest Coins 找零钱——多重背包+完全背包

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using std::max;
    using std::min;
    const int M=157,N=30007,inf=0x3f3f3f3f;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int ans,n,T,m,q[N],id[N],ql,qr,mx;
    int v[M],c[M],f[N],ly[N];
    int main(){
        //freopen("qwq.out","w",stdout);
        n=read(); T=read();
        for(int i=1;i<=n;i++) v[i]=read(),mx=max(mx,v[i]);
        for(int i=1;i<=n;i++) c[i]=read();
        m=mx*mx+T; for(int i=1;i<=m;i++) f[i]=ly[i]=inf;
        for(int i=1;i<=n;i++){
            for(int j=0;j<v[i];j++){
                ql=1; qr=0;
                for(int k=0,now;(now=k*v[i]+j)<m;k++){
                    int h=f[now]-k;
                    while(ql<=qr&&q[qr]>=h) qr--;
                    while(ql<=qr&&id[ql]<k-c[i]) ql++;
                    q[++qr]=h; id[qr]=k;
                    f[now]=min(inf,q[ql]+k);
                }
            }
        }
        for(int i=1;i<=n;i++) for(int j=v[i];j<=m;j++) ly[j]=min(ly[j],ly[j-v[i]]+1);
        ans=inf;
        for(int i=T;i<=m;i++) ans=min(ans,f[i]+ly[i-T]);
        printf("%d
    ",ans==inf?-1:ans);
        return 0;
    }
    View Code

     bzoj 1775: [Usaco2009 Dec]Vidgame 电视游戏问题——dp

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using std::max;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,p[55],k,c[55],w[55];
    int f[55][100007]; 
    int main(){
        n=read(); m=read();
        for(int i=1;i<=n;i++){
            p[i]=read(); k=read();
            for(int j=1;j<=k;j++){
                c[j]=read(); w[j]=read();
                for(int s=m;s>=c[j];s--) f[i][s]=max(f[i][s],max(f[i-1][s-c[j]]+w[j],f[i][s-c[j]]+w[j]));
            }
            for(int j=m;j>=p[i];j--) f[i][j]=max(f[i-1][j],f[i][j-p[i]]);
            for(int j=0;j<=p[i]-1;j++) f[i][j]=f[i-1][j];  
        }
        int ans=0; for(int i=0;i<=n;i++) ans=max(ans,f[i][m]); printf("%d
    ",ans);
        return 0;
    }
    View Code

     bzoj 1712: [Usaco2007 China]Summing Sums 加密——矩阵乘法

    这道题我们可以发现和(sum)每次都会乘(n-1)  所以单独考虑每一位就可以了 这样复杂度就可以接受了

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #define LL long long
    const int M=5e4+7,mod=98765431;
    LL read(){
        LL ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    LL sum,n,m,v[M];
    LL ans[3][3],b[3][3],c[3][3];
    void pmod(LL a[3][3],LL b[3][3]){
        memset(c,0,sizeof(c));
        for(int i=1;i<=2;i++) for(int k=1;k<=2;k++)
        for(int j=1;j<=2;j++) c[i][j]=(c[i][j]+a[i][k]*b[k][j]%mod+mod)%mod;
        for(int i=1;i<=2;i++) for(int j=1;j<=2;j++) a[i][j]=c[i][j];
    }
    int main(){
        n=read(); m=read();
        for(int i=1;i<=n;i++) v[i]=read(),sum=(sum+v[i])%mod;
        ans[1][1]=ans[2][2]=1;
        b[1][1]=-1; b[1][2]=1;
        b[2][1]=0;  b[2][2]=n-1;
        while(m){
            if(m&1) pmod(ans,b);
            pmod(b,b); m>>=1;
        }
        sum=(ans[1][2]*sum)%mod;
        for(int i=1;i<=n;i++) printf("%lld
    ",((ans[1][1]*v[i])%mod+sum+mod)%mod);
        return 0;
    }
    View Code

     bzoj 1916: [Usaco2010 Open]冲浪——dp 

    f[i][j]表示到点i失控j次的答案 注意按拓扑序来 从n到1逆着dp就可以了QAQ 拓扑的时候小心点 为此WA了3次QAQ

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    #define LL long long
    using std::max;
    using std::min;
    using std::queue;
    const int M=250000,N=100007;
    const LL inf=1e18;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,k,vis[N];
    LL f[N][15];
    int first[N],cnt,in[N];
    struct node{int to,next; LL w;}e[2*M];
    void ins(int a,int b,LL w){e[++cnt]=(node){b,first[a],w}; first[a]=cnt;}
    void insert(int a,int b,LL w){ins(a,b,w); ins(b,a,w);}
    queue<int>q;
    void topsort(int x){
        for(int i=first[x];i;i=e[i].next){
            int now=e[i].to;
            if(vis[now]) continue;
            if(!--in[now]) q.push(now),vis[now]=1;
        }
    }
    void solve(){
        int x=q.front(); q.pop();
        if(x==n){for(int i=1;i<=k;i++) f[x][i]=-inf; topsort(x); return ;}
        LL mn=inf,mx=-inf;
        for(int j=0;j<=k;j++){
            for(int i=first[x];i;i=e[i].next){
                int now=e[i].to;
                if(!vis[now]) continue;
                if(f[now][j]>=0) mx=max(mx,f[now][j]+e[i].w);
                if(j&&f[now][j-1]>=0) mn=min(mn,f[now][j-1]+e[i].w);
            }
            f[x][j]=mx<0?(mn<0?-inf:mn):(mn<0?mx:min(mx,mn));
        }
        topsort(x);
    }
    int main(){
        int x,y,w;
        n=read(); m=read(); k=read();
        for(int i=1;i<=m;i++){
            x=read(); y=read(); w=read();
            insert(x,y,w);
            in[x]++;
        }
        for(int i=1;i<=n;i++)if(!in[i]) q.push(i),vis[i]=1;
        while(!q.empty()) solve();
        printf("%lld
    ",f[1][k]);
        return 0;
    }
    View Code


    bzoj 2274: [Usaco2011 Feb]Generic Cow Protests——树状数组优化dp

    f[i]表示前i个数的方案数 这题本质上就是

    这里只要满足前缀和小于i的f[j]就可以辣 这个离散化一下前缀和然后树状数组维护一下就可以辣

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #define LL long long
    using std::sort;
    using std::unique;
    using std::lower_bound;
    const int M=2e5+7,mod=1e9+9;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    LL n,s[M];
    LL b[M],c[M],cnt;
    #define lowbit(x) x&-x
    void insert(int x,LL w){
        while(x<=cnt){
            s[x]=(s[x]+w)%mod; 
            x+=lowbit(x);
        }
    }
    LL query(int x){
        LL sum=0;
        while(x) sum=(sum+s[x])%mod,x-=lowbit(x);
        return sum;
    }
    int main(){
        n=read();
        for(int i=1;i<=n;i++) b[i]=b[i-1]+read(),c[++cnt]=b[i];
        cnt++; sort(c+1,c+1+cnt); cnt=unique(c+1,c+1+cnt)-c-1;
        for(int i=1;i<=n;i++) b[i]=lower_bound(c+1,c+1+cnt,b[i])-c;
        LL ans=lower_bound(c+1,c+1+cnt,0)-c;
        insert(ans,1);
        for(int i=1;i<=n;i++) ans=query(b[i]),insert(b[i],ans);
        printf("%lld
    ",ans);
        return 0;
    }
    View Code

     bzoj 3408: [Usaco2009 Oct]Heat Wave 热浪——最短路

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    const int M=1e4+7;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,S,T,d[M];
    int first[M],cnt;
    struct node{int to,next,w;}e[2*M];
    void ins(int a,int b,int w){e[++cnt]=(node){b,first[a],w}; first[a]=cnt;}
    void insert(int a,int b,int w){ins(a,b,w); ins(b,a,w);}
    struct pos{
        int id,d;
        bool operator <(const pos& x)const{return x.d<d;}
    };
    std::priority_queue<pos>q;
    void dj(){
        memset(d,0x3f,sizeof(d));
        d[S]=0; q.push((pos){S,d[S]});
        while(!q.empty()){
            pos x=q.top(); q.pop();
            if(x.d!=d[x.id]) continue;
            for(int i=first[x.id];i;i=e[i].next){
                int now=e[i].to;
                if(d[now]>d[x.id]+e[i].w) 
                d[now]=d[x.id]+e[i].w,q.push((pos){now,d[now]});
            }
        }
    }
    int main(){
        int x,y,w;
        n=read(); m=read(); S=read(); T=read();
        for(int i=1;i<=m;i++) x=read(),y=read(),w=read(),insert(x,y,w);
        dj();printf("%d
    ",d[T]);
        return 0;
    }
    View Code

     bzoj 2274: [Usaco2011 Feb]Generic Cow Protests——树状数组优化dp

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #define LL long long
    const int M=2e5+7,mod=1e9+9;
    using std::sort;
    using std::lower_bound;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,v[M],x[M],f[M],s[M];
    #define lowbit(x) x&-x
    void ins(int x,int v){while(x<=n) s[x]=(s[x]+v)%mod,x+=lowbit(x);}
    int query(int x){int sum=0; while(x) sum=(sum+s[x])%mod,x-=lowbit(x); return sum;}
    int main(){
        n=read();
        for(int i=1;i<=n;i++){
            v[i]=v[i-1]+read(); x[i]=v[i];
            if(v[i]>=0) f[i]=1;
        }
        sort(x+1,x+1+n);
        for(int i=1;i<=n;i++) v[i]=lower_bound(x+1,x+1+n,v[i])-x;
        for(int i=1;i<=n;i++){
            f[i]=(f[i]+query(v[i]))%mod;
            ins(v[i],f[i]);
        }printf("%d
    ",f[n]);
        return 0;
    }
    View Code

     bzoj 1740: [Usaco2005 mar]Yogurt factory 奶酪工厂——贪心

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #define LL long long
    const LL inf=1e15;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    LL n,s,k,mn=inf,ans;
    int main(){
        n=read(); s=read();
        for(int i=1;i<=n;i++){
            k=read();
            if(k-s*i<mn) mn=k-s*i;
            k=read(); ans=ans+(mn+s*i)*k;
        }printf("%lld
    ",ans);
        return 0;
    }
    View Code

     bzoj 1738: [Usaco2005 mar]Ombrophobic Bovines 发抖的牛——二分答案+网络流

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    #define LL long long
    using std::min;
    using std::max;
    const int M=557,Max=0x3f3f3f3f;
    const LL inf=1e15;
    int read(){
        int ans=0,f=1,c=getchar();
        while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}
        while(c>='0'&&c<='9'){ans=ans*10+(c-'0'); c=getchar();}
        return ans*f;
    }
    int n,m,S,T;
    LL tot,s[M][M],c[M],h[M],l,r;
    int first[5*M],cnt,cur[5*M];
    struct node{int to,next,flow;}e[M*M*2];
    void ins(int a,int b,int flow){e[++cnt]=(node){b,first[a],flow}; first[a]=cnt;}
    void insert(int a,int b,int flow){ins(a,b,flow); ins(b,a,0);}
    std::queue<int>q;
    LL d[5*M];
    int bfs(){
        memset(d,-1,sizeof(d));
        d[S]=0; q.push(S);
        while(!q.empty()){
            int x=q.front(); q.pop();
            for(int i=first[x];i;i=e[i].next){
                int now=e[i].to;
                if(e[i].flow&&d[now]==-1) d[now]=d[x]+1,q.push(now);
            }
        }
        return d[T]!=-1;
    }
    int dfs(int x,int a){
        if(x==T||!a) return a;
        int f,flow=0;
        for(int &i=cur[x];i;i=e[i].next){
            int now=e[i].to;
            if(d[now]==d[x]+1&&(f=dfs(now,min(a,e[i].flow)))>0){
                e[i].flow-=f; e[i^1].flow+=f;
                flow+=f;
                a-=f; if(!a) break;
            }
        }
        return flow;
    }
    bool check(LL k){
        S=0; T=2*n+1; cnt=1;
        memset(first,0,sizeof(first));
        for(int i=1;i<=n;i++) insert(S,i,c[i]),insert(i+n,T,h[i]);
        for(int i=1;i<=n;i++)
        for(int j=1;j<=n;j++)if(s[i][j]<=k) insert(i,j+n,Max);
        LL sum=0;
        while(bfs()){
            for(int i=0;i<=T;i++) cur[i]=first[i];
            sum+=dfs(S,Max);
        }
        return sum>=tot;
    }
    int main(){
        int x,y,w;
        n=read(); m=read();
        for(int i=1;i<=n;i++) c[i]=read(),h[i]=read(),tot+=c[i];
        for(int i=1;i<=n;i++) for(int j=1;j<=n;j++)if(i!=j) s[i][j]=inf;
        for(int i=1;i<=m;i++){
            x=read(); y=read(); w=read();
            s[x][y]=s[y][x]=min(s[x][y],1LL*w);
        }
        for(int k=1;k<=n;k++) for(int i=1;i<=n;i++)
        for(int j=1;j<=n;j++) s[i][j]=min(s[i][j],s[i][k]+s[k][j]);
        r=1e15;
        while(l<r){
            LL mid=(l+r)>>1;
            if(check(mid)) r=mid;
            else l=mid+1;
        }
        if(r==1e15) puts("-1");
        else printf("%lld
    ",r);
        return 0;
    }
    View Code
  • 相关阅读:
    IDataParameter调用存储过程
    ecshop下启用QQ在线服务,并能实时更新QQ在线状态
    交通部
    Java实现第九届蓝桥杯堆的计数
    Java实现第九届蓝桥杯全球变暖
    Java实现第九届蓝桥杯全球变暖
    Java实现第九届蓝桥杯堆的计数
    Java实现第九届蓝桥杯堆的计数
    Java实现第九届蓝桥杯全球变暖
    Java实现第九届蓝桥杯全球变暖
  • 原文地址:https://www.cnblogs.com/lyzuikeai/p/7337187.html
Copyright © 2011-2022 走看看