2014多校联合-第六场

最近这两场好无奈啊。。。

今天这场最后30分钟敲1001,压力倍增,虽然思路比较明确,但是代码打起来不怎么容易。

但是还是好在25分钟左右debug结束。提交wa,再提交,依然WA.......最后5分钟,还是没有AC掉。

一开始以为是精度问题,后来才sb的发现原来数组开小了。

在压力环境下保证代码的效率和质量真不是一件容易的事情。不过数组开小了,真是不可原谅。

1001:Map

题目相当于几条链表。把链表排成几行。

然后枚举每一列的状态会被操作多少次。

然后把和累加起来,然后直接除以状态总数。

#include <iostream>
#include<stdio.h>
#include<vector>
#include<queue>
#include<stack>
#include<string.h>
#include<algorithm>
#include <map>
using namespace std;
#define LL long long
#define lcm(a,b) (a*b/gcd(a,b))
int su[1010][1100];
int a[10100];
int have[1010];
int pre[10100];
int next[11000];
vector<int>vec;
int maxlen;
int pan(int p,int t)
{
    int n=vec.size();
    for(int i=0;i<n;i++)
    {
        if(t&(1<<i))
        {
            if(su[i][p]==0)return 0;
        }
    }
    return 1;
}
double use(int p,int t)
{
    int n=vec.size();
    int s,x,y;
    x=have[p];
    y=0;
    s=0;
    for(int i=0;i<n;i++)
    {
        if(t&(1<<i))
        {
            y++;
            s+=a[su[i][p]];
        }
    }
    if(y>1)
    {
        return 1.0*y*s/x+s;
    }
    else return s;
}
void dos()
{
    int n=vec.size();
    int t=1<<n;
    t--;
    double ans=0;
    double pp=1.0;
    for(int i=0;i<n;i++)
    {
        pp*=1.0*(su[i][0]+1);
    }
    pp--;
    for(int i=1;i<=maxlen;i++)
    {
        for(int j=1;j<=t;j++)
        {
            if(pan(i,j)==0)continue;
            double sum=use(i,j);
            double ch=1.0;
            for(int k=0;k<n;k++)
            {
                if(j&(1<<k))
                {
                    ch*=1.0*(su[k][0]-i+1);
                }
                else
                {
                    ch*=1.0*min((su[k][0]+1),i);
                }
            }
            ans+=sum*ch;
        }
    }
    printf("%.3f\n",ans/pp);
}
int main()
{
    int T,n,m;
    scanf("%d",&T);
    while(T--)
    {
        memset(have,0,sizeof(have));
        memset(pre,0,sizeof(pre));
        memset(next,-1,sizeof(next));
        scanf("%d%d",&n,&m);
        for(int i=1;i<=n;i++)
        {
            scanf("%d",&a[i]);
        }

        int u,v;
        while(m--)
        {
            scanf("%d%d",&u,&v);
            u++;
            v++;
            pre[v]=u;
            next[u]=v;
        }
        vec.clear();
        for(int i=1;i<=n;i++)
        {
            if(pre[i]==0)vec.push_back(i);
        }
        memset(su,0,sizeof(su));
        maxlen=0;
        for(int i=0;i<vec.size();i++)
        {
            int k=1;
            for(int j=vec[i];j!=-1;j=next[j])
            {
                su[i][k]=j;
                have[k]++;
                k++;
            }
            su[i][0]=k-1;
            maxlen=max(maxlen,k-1);
        }
        dos();
    }
    return 0;
}

1003:Room and Moor

从前往后扫,如果不满足不下降,就把后面的合并到前面去,如果还不满足,继续合并。

最后算出结果即可。

#include <iostream>
#include<stdio.h>
#include<vector>
#include<queue>
#include<stack>
#include<string.h>
#include<algorithm>
#include<math.h>
using namespace std;
#define eps 1e-9
#define zero(x) (fabs(x)<eps?0:x)
#define maxn 110000
struct list
{
    int x;
    int y;
    double f;
    int pre;
}p[maxn];
int a[maxn];
double su(int x,int y)
{
    return (1.0*x)/(1.0*x+1.0*y);
}
void dos(int n)
{
    p[0].f=0.0;
    p[0].pre=-1;
    p[0].x=0;
    p[0].y=0;
    for(int i=1;i<=n;i++)
    {
        p[i].f=su(p[i].x,p[i].y);
     //   cout<<i<<" "<<p[i].x<<" "<<p[i].y<<" "<<p[i].f<<endl;
        if(zero(p[i].f-p[i-1].f)>=0)
        {
            p[i].pre=i-1;
            continue;
        }
        for(int j=i-1;j!=-1;j=p[j].pre)
        {
            p[i].x+=p[j].x;
            p[i].y+=p[j].y;
            p[i].pre=p[j].pre;
            p[i].f=su(p[i].x,p[i].y);
            if(zero(p[i].f-p[p[i].pre].f)>=0)break;
        }
    }
    double sum=0.0;
    for(int i=n;i!=-1;i=p[i].pre)
    {
        double ps=0;
        double f=p[i].f;
        ps+=f*f*1.0*p[i].y;
        f=1.0-f;
        ps+=f*f*1.0*p[i].x;
        sum+=ps;
    }
    printf("%.6f\n",sum);
}
int main()
{
    int T,n;
    scanf("%d",&T);
    while(T--)
    {
        scanf("%d",&n);
        for(int i=1;i<=n;i++)
        {
            scanf("%d",&a[i]);
        }
        int ls=0;
        int leap=1;
        for(int i=1;i<=n;i++)
        {
            if(ls==0)
            {
                if(a[i]==0)continue;
                else
                {
                    ls++;
                    p[ls].x=1;
                    p[ls].y=0;
                    continue;
                }
            }
            if(leap==a[i])
            {
               if(leap==0)p[ls].y++;
               else p[ls].x++;
            }
            else
            {
                leap=leap^1;
                if(leap==1)
                {
                    ls++;
                    p[ls].x=0;
                    p[ls].y=0;
                }
                i--;
            }
          //  cout<<ls<<" "<<p[ls].x<<" "<<p[ls].y<<endl;
        }
        if(p[ls].y==0)ls--;
     //   cout<<"__"<<ls<<endl;
        if(ls==0)
        {
            printf("%.6f\n",1.0*ls);
            continue;
        }
        dos(ls);
    }
    return 0;
}

1005:Apple Tree

很明显可以发现,我们交叉放苹果和肥料是最优的,一共两种放法。

直接模拟一下就好。

1007:Series 1

脱脱的最后的系数是一个杨辉三角。然后+,-交替。

不过是大数sad,要用到java。。。

悲伤

import java.util.Scanner;
import java.math.*;

public class Main {
    public static void main(String[] args) {
        Scanner cin = new Scanner(System.in);
        BigInteger[] bit = new BigInteger[3300];
        BigInteger ans,temp,sn;

        int i,cas,n,j,k;
        cas = cin.nextInt();
        for(i = 1;i <= cas;i ++)
        {
            ans = BigInteger.ZERO;
            temp = BigInteger.ONE;
            n = cin.nextInt();
            sn = BigInteger.valueOf(n-1);
            for(j = 1;j <= n;j ++)
                bit[j] = cin.nextBigInteger();
            for(j = 0;j < n;j ++)
            {
                if(j%2 == 0)
                    ans = ans.add(temp.multiply(bit[n-j]));
                else
                    ans = ans.subtract(temp.multiply(bit[n-j]));
                temp = temp.multiply(sn).divide(BigInteger.valueOf(j+1));
                sn = sn.subtract(BigInteger.ONE);
            }
            System.out.println(ans);
        }
    }
}

1010:Fighting the Landlords

这个题目就不吐槽了。。。

很明显一开始看错题了。。。

就是一个水的模拟题,不用理会。。。。

2014多校联合-第六场,布布扣,bubuko.com

时间: 2024-12-17 06:21:13

2014多校联合-第六场的相关文章

hdu5353||2015多校联合第六场1001 贪心

http://acm.hdu.edu.cn/showproblem.php?pid=5353 Problem Description There are n soda sitting around a round table. soda are numbered from 1 to n and i-th soda is adjacent to (i+1)-th soda, 1-st soda is adjacent to n-th soda. Each soda has some candies

2014多校联合-第七场

1005: ( Stupid Tower Defense ) 由题意我们很明显可以知道,红色的塔放在最后面是最优的. 假如前i个塔,放j个绿塔,i-j个蓝塔.那么无论前i个塔的顺序怎么放,对后面的塔造成的影响是完全相同的. dp[i][j]:前i个塔,放j个绿塔,能获得的最大价值. dp[i][j]=max(dp[i-1][j-1]+当前塔放绿塔获得的能量值,dp[i-1][j]+当前塔放蓝塔获得的能量值): #include <iostream> #include<stdio.h>

2014多校联合-第八场

1001:2048 很明显,一开始看错题了...sad 这题目我感觉挺卡时间的... dp[i][j]:在选择2^i的时候,选择的和为j*2^i到(j+1)*2^i-1时候的情况. #include <iostream> #include<stdio.h> #include<vector> #include<queue> #include<stack> #include<string.h> #include<algorithm&

HDOJ多校联合第六场

先一道一道题慢慢补上, 1009.题意,一棵N(N<=50000)个节点的树,每个节点上有一个字母值,给定一个串S0(|S0| <=30),q个询问,(q<=50000),每次询问经过两个点u,v之间的路径上的字母构成字符串S,问S0在S中作为序列出现了多少次. 分析:对于每次询问需要知道其LCA,设w = LCA(u, v),可以用tarjan处理出来,或者倍增法也行.然后w会将S0分成两部分,记做S1,S2,然后分别考虑S1在u->w的路径出现次数,以及S2在v->w出现

2014多校联合-第五场

1001:Inversion 模版题,求逆序数对.有多少逆序数对,就可以剪掉多少. 1003:Least common multiple 对于每一个子集,lcm为2的a的最大值次方*3的b的最大值次方. 所以我们只需要求出以某个b为b的最大值的时候,a的最大值的分布情况即可. 我们先把b从小到大排序. 对于某一个b,我门只需要求出之前出现过的a比当前a小的数量为x: 那么就可知对于这些a的子集,为2^x个,并且,每个子集a的最大值都为当前a. 我么还需要求出对于大于当前a的a有多少个比a小的数,

2014多校联合训练第一场(组队训练)

这是我.potaty.lmz第二次训练,毕竟经验不足,加上水平不够,导致我们各种被碾压. A - Couple doubi: 这道题是道比较水的数论.但我们都没想出来要怎么做.后来是potaty提议打个表看看,然后lmz打出表后发现了规律.我还没细看,待研究后再补全. D - Task: 这道题一看就知道是个贪心(现在只要是有deadline的题我都觉得是贪心了).虽然想出来了,但还是不会严格证明为什么只要取满足task的且y最小(y相等时x最小)的machine就行了. 我的做法是把所有mac

HDU 5793 A Boring Question (费马小定理) ---2016杭电多校联合第六场

A Boring Question Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/Others)Total Submission(s): 156    Accepted Submission(s): 72 Problem Description There are an equation.∑0≤k1,k2,?km≤n∏1?j<m(kj+1kj)%1000000007=?We define t

HDU 5795 A Simple Nim (博弈) ---2016杭电多校联合第六场

A Simple Nim Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/Others)Total Submission(s): 79    Accepted Submission(s): 48 Problem Description Two players take turns picking candies from n heaps,the player who picks the las

2014多校联合六(HDU 4923 HDU 4925 HDU 4927 HDU 4930)

HDU 4923 Room and Moor 题意:给出A序列  求满足题目所写的B序列  使得方差最小 思路:可以想到最后的结果中  B序列的值一定是一段一段的  那么我们可以类似贪心去搞  对于一段序列我们可以求出什么样的b值使得方差最小  即序列中1的个数除以序列长度  又因为B是单调的  可以用一个单调栈去模拟  复杂度远远小于n^2  不要被吓怕- 代码: #include<cstdio> #include<cstring> #include<algorithm&g