• 2021寒假结训比赛


    (w[i][j] * w[j][k] * .... * w[p][i]<1成立)

    考试要认真看题啊哥!你怎么自动认为p i 是 p l呢。。。。。

    (圆周上面有n个位置可以绑上细线,可以这样把n个位置两两连接,然后在这个圆上产生很多的交点。)
    就是(C(n,4))

    CSU-1980 不堪重负的树

    由于给出的是二叉树,且是中序遍历,所以该题可以用区间DP(枚举左端点和len)

            for(int l=2;l<=n;l++)
    	{
    	    for(int i=1;i+l-1<=n;i++)
    		{
    		 int j=i+l-1;
    		 dp[i][j]=inf;
    		 for(int k=i;k<=j;k++) 
    		   dp[i][j]=min(dp[i][j],dp[i][k-1]+dp[k+1][j]+sum[j]-sum[i-1]);
    		}
    		
    	}
    

    【BZOJ1575】【USACO 2009 OPEN】 气象牛Baric

    f[i][j]表示最后一个i为必选,一共选了j个元素。

    预处理三种误差:

    1:从头到k的误差pre

    2:从k到最后一个数的误差suf

    3:【i+1,j-1】区间所有数对mid的误差

    转移方程为:(f[i][j]=min{f[i][j],f[k][j-1]-suf[k]+med[k][i]+suf[i]})

    画个图就很直白了

     1 #include<stdio.h>
     2 #include<string.h>
     3 #include<algorithm>
     4 #include<math.h>
     5 //#include<iostream>
     6 using namespace std;
     7 
     8 int n,E;
     9 #define maxn 111
    10 int suf[maxn],pre[maxn],med[maxn][maxn],f[maxn][maxn],a[maxn];
    11 const int inf=0x3f3f3f3f;
    12 int main()
    13 {
    14     scanf("%d%d",&n,&E);
    15     for (int i=1;i<=n;i++) scanf("%d",&a[i]);
    16     for (int i=1;i<=n;i++)
    17     {
    18         pre[i]=0;
    19         for (int j=1;j<i;j++)
    20             pre[i]+=2*fabs(a[j]-a[i]);
    21     }
    22     for (int i=n;i>=1;i--)
    23     {
    24         suf[i]=0;
    25         for (int j=i+1;j<=n;j++)
    26             suf[i]+=2*fabs(a[j]-a[i]);
    27     }
    28     for (int i=1;i<=n;i++)
    29         for (int j=i;j<=n;j++)
    30         {
    31             med[i][j]=0;
    32             for (int k=i+1;k<j;k++)
    33                 med[i][j]+=fabs(2*a[k]-a[i]-a[j]);
    34         }
    35     int ans=0,lest=inf;
    36     for (int i=1;i<=n;i++)
    37     {
    38         f[i][1]=pre[i]+suf[i];
    39         if (f[i][1]<=E) {ans=1;lest=min(lest,f[i][1]);}
    40     }
    41     for (int j=2;!ans && j<=n;j++)
    42         for (int i=1;i<=n;i++)
    43         {
    44             f[i][j]=inf;
    45             for (int k=1;k<i;k++)
    46                 f[i][j]=min(f[i][j],f[k][j-1]-suf[k]+suf[i]+med[k][i]);
    47             if (f[i][j]<=E) {ans=j;lest=min(lest,f[i][j]);}
    48         }
    49     printf("%d %d
    ",ans,lest);
    50     return 0;
    51 }
    

    5.CSU_1987

    trie数,再加个数组纪录这个点的深度

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #define maxl 10000010
    
    using namespace std;
    
    int n,sz,cas,cnt,ans;
    int dis[maxl],val[maxl];
    int ch[maxl][3];
    char s[maxl];
    
    void prework()
    {
    	memset(ch,0,sizeof(ch));
    	memset(dis,0,sizeof(dis));
    	memset(val,0,sizeof(val));
    	scanf("%d",&n);
    }
    
    void insert()
    {
    	int len=strlen(s),u=0,v,c;
    	for(int i=0;i<len;i++)
    	{
    		c=s[i]-'0';
    		if(!ch[u][c])
    		{
    			sz++;ch[u][c]=sz;
    			dis[sz]=dis[u]+1;
    		}
    		u=ch[u][c];
    		val[u]++;
    		if(val[u]*dis[u]>ans)
    			ans=val[u]*dis[u];
    	}
    }
    
    void mainwork()
    {
    	ans=0;sz=0;
    	for(int i=1;i<=n;i++)
    	{
    		scanf("%s",s);
    		insert();
    	}
    }
    
    void print()
    {
    	printf("%d
    ",ans);
    }
    
    int main()
    {
    	int t;
    	scanf("%d",&t);
    	for(int i=1;i<=t;i++)
    	{
    		prework();
    		mainwork();
    		print();
    	}
    	return 0;
    } 
    
    

    6.区间内比k小的数

    离线+树状数组

    bool cmp1(const num &x,const num &y){
    	return x.x<y.x;
    }
    
    bool cmp2(const que &x,const que &y){
    	return x.x<y.x;
    }
    
    void prework(){
    	n=read();m=read();
    	for(int i=1;i<=n;i++)
    		a[i].x=read(),a[i].ind=i,b[i]=0;
    	sort(a+1,a+1+n,cmp1);
    	for(int i=1;i<=m;i++){
    		q[i].l=read();q[i].r=read();
    		q[i].x=read();q[i].ind=i;
    	}
    	sort(q+1,q+1+m,cmp2);
    }
    
    void add(int i,int x){
    	while(i<=n){
    		b[i]+=x;
    		i+=i&-i;
    	}
    }
    
    int sum(int i)
    {
    	int s=0;
    	while(i)
    	{
    		s+=b[i];
    		i-=i&-i;
    	}
    	return s;
    }
    
    void mainwork()
    {
    	int at=0;
    	for(int i=1;i<=m;i++)
    	{
    		while(at<n && a[at+1].x<q[i].x)
    			at++,add(a[at].ind,1);
    		ans[q[i].ind]=sum(q[i].r)-sum(q[i].l-1);
    	}
    }
    

    CSUOJ 2151 区间赋值,区间加,使用分块与两个tag

    #include<bits/stdc++.h>
    #define N 100005
    #define NN 500
    #define ll long long
    const int INF=1e9;
    using namespace std;
    
    int n,m,v0,a[N],num,block,belong[N],ri[N],le[N];
    ll tag1[NN],tag2[NN];
    
    long long sum[NN];
    
    void build() { 
            block=sqrt(n); 
            num=n/block; 
            if(n%block) ++num; 
            for(int i=1 ; i <= n ; ++i) {
                belong[i]=(i-1)/block+1; 
            }
            for(int i=1 ; i <= num ; ++i) {
                le[i]=(i-1)*block+1;
                ri[i]=i*block; 
            }
            ri[num]=n; 
            for(int i=1 ; i <= num ; ++i) {
                   for(int j=le[i] ; j <= ri[i] ; ++j) { 
                       sum[i] += a[j];
                }
            }
        } 
    void Tagdown(int i){
        if(tag2[i]==-INF){
            if(tag1[i]!=-INF){
                sum[i]=0;
                for(int j=le[i];j<=ri[i];j++){
                    a[j]+=tag1[i];
                    sum[i]+=a[j];
                }
                     tag1[i]=-INF;
            }
        }
        else{
            sum[i]=0;
            for(int j=le[i];j<=ri[i];j++){
                a[j]=tag2[i];
                sum[i]+=a[j];
            }
            tag2[i]=-INF;
        }
    }
    void modify(int l,int r,int v,bool op) {  
            if(belong[l]==belong[r]){ 
                    Tagdown(belong[l]);
                    
                    for(int i=l;i<=r;++i) { 
                        if(!op){
                            a[i] += v;
                            sum[belong[i]] += v;
                        } 
                        else{
                            sum[belong[i]] += (v-a[i]);
                            a[i]=v;
                        }
                    }
                    return;
            }  
    
    
                Tagdown(belong[l]);
                Tagdown(belong[r]);  
    
    
    
            for(int i=l;i <= ri[belong[l]];++i) { 
                    if(!op){
                        a[i] += v;
                        sum[belong[i]] += v;
                    } 
                    else{
                        sum[belong[i]] += (v-a[i]);
                        a[i]=v;
                    }
            }
            for(int i=le[belong[r]];i <= r;++i) { 
                    if(!op){
                        a[i] += v;
                        sum[belong[r]]+=v;
                    } 
                    else{
                        sum[belong[i]] += (v-a[i]);
                        a[i]=v;
                    }
            }
    
            for(int i=belong[l]+1 ; i<belong[r] ; ++i) { 
                 if(!op){
                        if(tag2[i]!=-INF){
                            tag2[i] += v; 
                            sum[i]=tag2[i]*(ri[i]-le[i]+1);
                        }
                        else {
                            if(tag1[i]==-INF)tag1[i]=v;
                            else tag1[i] += v;
                            sum[i] += v*(ri[i]-le[i]+1);
                        }
                    } 
                    else{
                         tag2[i]=v;
                         tag1[i]=-INF;
                         sum[i]=v*(ri[i]-le[i]+1);
                    }
            }  
    }
    //3.区间查询  
    ll query(int l,int r) { 
     
            ll ans=0;
    
            
            if(belong[l]==belong[r]){
                 for(int i=l;i <= r ;++i) {  
                    if(tag2[belong[i]]!=-INF)ans += tag2[belong[i]];
                    else if(tag1[belong[i]]!=-INF)ans += a[i]+tag1[belong[i]];
                    else ans += a[i];
                }
    
                return ans;
            }
    
            for(int i=l;i <= ri[belong[l]];++i) {  
                if(tag2[belong[i]]!=-INF)ans += tag2[belong[i]];
                else if(tag1[belong[i]]!=-INF)ans += a[i]+tag1[belong[i]];
                else ans += a[i];
            }
    
            for(int i=le[belong[r]];i <= r;++i) { 
                if(tag2[belong[i]]!=-INF)ans += tag2[belong[i]];
                else if(tag1[belong[i]]!=-INF)ans += a[i]+tag1[belong[i]];
                else ans += a[i];
            } 
            for(int i=belong[l]+1 ; i<belong[r] ; ++i) {    
                       ans += sum[i];
            }  
            return ans;
    }
    
    
    int main(){
    
        scanf("%d%d%d",&n,&m,&v0); 
        for(int i=1;i <= n;i++)a[i]=v0;
        build();
        for(int i=1;i <= num;i++){
            tag1[i]=tag2[i]=-INF;
        }
        while(m--){
            int x,y,v,op;
            scanf("%d%d%d",&op,&x,&y);
            if(op!=2){
                scanf("%d",&v);
                modify(x,y,v,op);
            }
            else printf("%lld
    ",query(x,y)); 
        }
        return 0; 
    }
    
  • 相关阅读:
    vue input输入框验证10的n次方
    Django2.2使用mysql数据库pymysql版本不匹配问题的解决过程与总结
    数据结构(四):树
    数据结构(三):队列
    数据结构(二):栈
    数据结构(一):链表
    python深拷贝与浅拷贝
    python yield、yield from与协程
    python __getattribute__、__getattr__、__setattr__详解
    python迭代、可迭代对象、迭代器及生成器
  • 原文地址:https://www.cnblogs.com/GUOGaby/p/14563292.html
Copyright © 2020-2023  润新知