一大坨模拟赛水题~(数据是不水的233)

比赛链接https://www.luogu.org/contest/show?tid=1084(md找不到超链接2333)

/*Dfs找最长半径(自己编的 不知道叫啥2333)*/
#include<cstdio>
#define maxn 50010
using namespace std;
int n,num,head[maxn],sum;
struct node{
    int v,t,pre;
}e[maxn*2];
int init(){
    int x=0,f=1;char s=getchar();
    while(s<'0'||s>'9'){if(s=='-')f=-1;s=getchar();}
    while(s>='0'&&s<='9'){x=x*10+s-'0';s=getchar();}
    return x*f;
}
int max(int x,int y){
    return x>y?x:y;
} 
void Add(int from,int to,int dis){
    num++;e[num].v=to;
    e[num].t=dis;
    e[num].pre=head[from];
    head[from]=num;
}
int Dfs(int x,int from){
    int r=0;
    for(int i=head[x];i;i=e[i].pre){
        int v=e[i].v;if(v==from)continue;
        r=max(r,Dfs(v,x)+e[i].t);
    }
    return r;
}
int main()
{
    n=init();int u,v,t;
    for(int i=1;i<n;i++){
        u=init();v=init();t=init();
        Add(u,v,t);Add(v,u,t);sum+=t;
    }
    printf("%d\n",sum*2-Dfs(1,0));
    return 0;
}
/*找环+记忆化Dfs (自己yy的不是正解 但也挺快的)*/
#include<iostream>
#include<cstdio>
#define maxn 500010
#define ll long long
using namespace std;
int n,A[maxn],d[maxn],sum,belong[maxn],size[maxn];
int dfn[maxn],low[maxn],topt,f[maxn],s[maxn],top;
ll ans,dp[maxn],len[maxn];
int init(){
    int x=0;char s=getchar();
    while(s<'0'||s>'9')s=getchar();
    while(s>='0'&&s<='9'){x=x*10+s-'0';s=getchar();}
    return x;
}
void dfs(int x){
    low[x]=dfn[x]=++topt;
    f[x]=1;s[++top]=x;
    int v=A[x];
    if(dfn[v]==0){
        dfs(v);low[x]=min(low[v],low[x]);
    }
    else if(f[v])low[x]=min(low[x],dfn[v]);
    if(low[x]==dfn[x]){
        sum++;
        while(x!=s[top]){
            len[sum]+=d[s[top]];f[s[top]]=0;
            belong[s[top]]=sum;top--;size[sum]++;
        }
        len[sum]+=d[s[top]];f[s[top]]=0;
        belong[s[top]]=sum;top--;size[sum]++;
    }
}
void Tarjan(){
    for(int i=1;i<=n;i++)
        if(dfn[i]==0)dfs(i);
    for(int i=1;i<=n;i++)
        if(size[belong[i]]>1)
            dp[A[i]]=len[belong[i]]-d[i];
}
ll Dfs(int x){
    if(dp[x])return dp[x];
    dp[x]=d[x]+Dfs(A[x]);
    return dp[x];
}
int main()
{
    n=init();
    for(int i=1;i<=n;i++){
        A[i]=init();d[i]=init();
    }
    Tarjan();
    for(int i=1;i<=n;i++)
        ans=max(ans,Dfs(i));
    cout<<ans<<endl;
    return 0;
}
/*研究好题目 nlon LIS*/
#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
#define maxn 100010
using namespace std;
int n,x,c[maxn],num;
int init(){
    int x=0;char s=getchar();
    while(s<'0'||s>'9')s=getchar();
    while(s>='0'&&s<='9'){x=x*10+s-'0';s=getchar();}
    return x;
}
int main()
{
    n=init();c[0]=-0x7fffffff;
    for(int i=1;i<=n;i++)
      {
          x=init();
          if(x>c[num]){c[++num]=x;continue;}
        int p=lower_bound(c+1,c+1+num,x)-c;
        c[p]=x;
      }
    printf("%d\n",num);
    return 0;
}
/*
之前做的时候n只有1000 这就比较好了 n*n暴力搞
今天比赛看到 我X 这么大的数据 丧心病狂啊直接
然后研究了std233333
nlogn的做法最大的两个点h才100 有套路 一片一片的搞
行列的h顺序无所谓 先排序 把一样高的挨起来搞
然后找一样高的 自己脑补一下图吧
(n,m)处的高度为H 然后向左下移动
一块小矩形都是H 体积可算
那剩下的矩形头顶和右边那一块也能确定高度 
啦啦啦说不清楚啊 自己画图脑补一下吧23333

再来吐槽一下神数据 sort卡掉 merge卡掉
逼得我用桶排23333
*/
#include<iostream>
#include<cstdio>
#include<cstring>
#define maxn 5000001
#define ll long long
using namespace std;
int n,m,mxl[maxn],mxc[maxn],sl[maxn],sc[maxn],c[maxn],Tong1[1010],Tong2[1010];
ll mx,mi;
int init(){
    int x=0;char s=getchar();
    while(s<'0'||s>'9')s=getchar();
    while(s>='0'&&s<='9'){x=x*10+s-'0';s=getchar();}
    return x;
}
void Tong_sort(){
    for(int i=0;i<=1000;i++)
        for(int j=1;j<=Tong1[i];j++)
            mxl[++n]=i;
    for(int i=0;i<=1000;i++)
        for(int j=1;j<=Tong2[i];j++)
            mxc[++m]=i;
}
int main()
{
    n=init();m=init();int x;
    for(int i=1;i<=n;i++){
        x=init();Tong1[x]++;
    }
    for(int i=1;i<=m;i++){
        x=init();Tong2[x]++;
    }
    n=m=0;
    Tong_sort();
    for(int i=1;i<=n;i++)sl[i]=sl[i-1]+mxl[i];
    for(int i=1;i<=m;i++)sc[i]=sc[i-1]+mxc[i];
    while(n||m){
        int h=max(mxl[n],mxc[m]);
        int s1=0,s2=0;
        while(n&&mxl[n]==h)n--,s1++;
        while(m&&mxc[m]==h)m--,s2++;
        mx+=(ll)s1*s2*h+(ll)s1*sc[m]+(ll)s2*sl[n];
        mi+=(ll)max(s1,s2)*h;
    }
    cout<<mi<<" "<<mx<<endl;
    return 0;    
}

 

posted @ 2016-10-22 08:19  一入OI深似海  阅读(256)  评论(0编辑  收藏  举报