zoukankan      html  css  js  c++  java
  • SDUSTOJ 1795 哆啦A梦的程序(思路题)

    Description

    哆啦A梦很喜欢写代码。在缩代码方面,他是一位身经百战的老手。世界各地的OJ上,很多题的最短解答排行榜都有他的身影。这令他感到十分愉悦。


    最近,他突然发现,很多时候自己的程序明明看起来比别人的更短,实际代码量却更长。这令他感到很费解。经过一番研究,原来是因为他每一行的缩进都全是由空格组成的,大量的空格让代码量随之增大。

    现在设哆啦A梦有一份 n 行的代码,第 i 行有 ai 个空格作为缩进。

    为解决这一问题,哆啦A梦要给自己文本编辑器设定一个正整数的默认TAB宽度 x,然后对于每一行,编辑器从头至尾不断把连续 x 个空格替换成一个TAB,直到剩余空格数不足 x 个。

    最终缩进所占代码量为空格数与TAB数的和。请你帮哆啦A梦选择一个合适的 x,使得缩进所占代码量最小。

    Input

    多组数据,对于每一组数据

    第一行一个正整数 n,表示代码行数。

    接下来 n 行,第 i行一个正整数 ai,为初始时第 i行缩进的空格个数。

    n<=10^6,ai<=10^6

    Output

    一行一个整数,表示缩进所占代码量最小是多少。

    Sample Input

    3
    5
    8
    8

    Sample Output

    6
    
    思路:
    这道题是山科第三届校赛的题,我们队一路领先,直到最后20分钟被这道题绝杀了。。
    真的是一时想不出好的思路,练得太少了,弱就是弱
    这道题据出题人说正解是nlogn的复杂度,想好了思路就很简单,但是三分答案也能过
    赛后整理了一下,说一下我的做法吧
    枚举x(o(n)),每一层以x长度分段
    也就是for(int j=1;j*x<=n;j++)这样分
    每一个x长度的段里所有数的个数和所有数的和都可以o(n)预处理
    然后当前这一个x的ans加上个数*j(除法的值),再加上这一层的和减去着一层的个数*i*j(取模的值)
    这样每一个x都可以给出一个确定的答案
    时间复杂度就是O(n/1+n/2+n/3+...+n/n)=O(nlogn)的了
    可能我写的比较复杂、、比标程长,也慢(实力差距~)
    /* ***********************************************
    Author        :devil
    Created Time  :2016/4/26 16:10:39
    ************************************************ */
    #include <cstdio>
    #include <cstring>
    #include <iostream>
    #include <algorithm>
    #include <vector>
    #include <queue>
    #include <set>
    #include <map>
    #include <string>
    #include <cmath>
    #include <stdlib.h>
    using namespace std;
    typedef long long LL;
    const int N=2e6+7;
    int a[N],b[N];
    long long sum[N];
    int main()
    {
        //freopen("in.txt","r",stdin);
        int n,x;
        while(~scanf("%d",&n))
        {
            int ma=0;
            memset(a,0,sizeof(a));
            memset(b,0,sizeof(b));
            memset(sum,0,sizeof(sum));
            for(int i=0;i<n;i++)
            {
                scanf("%d",&x);
                ma=max(ma,x);
                a[x]++;
            }
            for(int i=1;i<=ma*2+1;i++)
            {
                sum[i]=sum[i-1]+a[i]*i;
                b[i]=b[i-1]+a[i];
            }
            LL ans=1e12+10;
            for(int i=1;i<=ma;i++)
            {
                LL now=sum[i-1];
                for(int j=1;i*j<=ma;j++)
                    now=now+(b[i*(j+1)-1]-b[i*j-1])*j+sum[i*(j+1)-1]-sum[i*j]-(b[i*(j+1)-1]-b[i*j])*j*i;
                ans=min(ans,now);
            }
            printf("%lld
    ",ans);
        }
        return 0;
    }
  • 相关阅读:
    Silverlight4 GDR3与Silverlight5 EAP1的变化
    使用微软WPF技术开发产品优势究竟在那里
    于娟——《活着就是王道》博客精华文摘
    Silverlight中开发和设计人员的合作
    ubuntu10.10编译内核步骤
    添加系统调用实验步骤
    SinaWeiboSdk c++test
    【转】windows7下硬盘安装linux,双系统共存
    cppunit在vs2008下使用的环境搭建(上)
    【转】RedHat Linux 5 安装 OpenOffice 3.2.0
  • 原文地址:https://www.cnblogs.com/d-e-v-i-l/p/5435509.html
Copyright © 2011-2022 走看看