`
Coco_young
  • 浏览: 127762 次
  • 性别: Icon_minigender_1
  • 来自: 湖南长沙
社区版块
存档分类
最新评论

[动态规划+数学结论]HOJ_12301_Eleven Lover

 
阅读更多

题目来源:HNU http://acm.hnu.cn/online/?action=problem&type=show&id=12301&courseid=214

题目大意:给定一个数字(0-9)序列,没有前导0,要求你求出所有这样的连续子序列,即该子序列为11的倍数(0不算),序列长度可以达到80000

分析:要求解的实际上是两个子问题,1.如何判断一个序列能整除11,2.如何求出所有的这种序列。很容易想到,枚举起点终点,然后做大数取模,如果能整除11,那么记录下来,这样做的复杂度能达到O(n^3),显然会超时。那么,这里需要用到一个结论:在Radix进制下的数%(Radix+1)==0的充要条件是,该数的奇数位之和减去偶数位之和(以下记为隔位差)能够整除(Radix+1),同样还有另外一个结论,Radix进制下得数%(Radix-1)==0的充要条件是,该数的所有位之和能够整除(Radix-1)。这样的话,实际上如果要枚举起点终点的方法,还是不能够降低复杂度,这里要利用该结论用DP来解决。

构造状态为dp(i,j)表示以第i位结尾的所有子串的隔位差%11==j的个数,那么状态空间是11*80000,现在考虑如何进行转移,这里要感谢瑞瑞给的一个证明:对于序列ai-a1(假设i为偶数),记其隔位差为s,即s = segma(aj){0<j<i&&j is odd}-segma(ak){0<k<=i&&k is even},那么序列ai+1-a1的隔位差为ai+1-s,这里给出一个证明的样例,假设当前序列为abcd,那么其隔位差为(a+c)-(b+d),那么考虑到abcdf,其隔位差为(f+c+a)-(b+d) = f - [(a+c)-(b+d)] = f-s,即证。

再结合模的性质

那么可以得出状态转移方程为

dp(0,a1%11) = 1

dp(i,(ai%11-j)mod11) += dp(i-1,j){0<i<L,0<=j<11} && if(ai) dp(i,ai%11)++ ,其中mod的作用是取模,返回值为0-10。最后的结果就是segma(dp(i,0)){0<=i<L}

考虑到dp(i,j)只与dp(i-1,k)有关系,那么可以用滚动数组优化。

代码:

#include<iostream>
#include<cstring>
#include<cstdio>
using namespace std;
const int MAXN = 80011; 
char seq[MAXN];
int dp[2][11];
int mod11(int x)
{
    x%=11;
    if(x<0)return x+11;
    return x;
}
int main()
{
    int L,ans;
    while(gets(seq),seq[0]!='0')
    {
        memset(dp,0,sizeof(dp));ans = 0;L = strlen(seq);
        dp[0][seq[0]-'0']=1;
        for(int i=1;i<L;i++)
        {
            int s = seq[i]-'0';
            for(int j=0;j<11;j++)
            {
                dp[1][mod11(s%11-j)]+=dp[0][j];
            }
            if(s)dp[1][s%11]++;
            ans+=dp[1][0];
            memcpy(&dp[0][0],&dp[1][0],11*sizeof(int));
            memset(dp[1],0,11*sizeof(int));
        }
        /*for(int i=0;i<L;i++)
        {
            for(int j=0;j<11;j++)
            cout<<dp[i][j]<<" ";
            cout<<endl;
        }*/
        printf("%d\n",ans);
    }
    return 0;
}


总结:在状态转移时,开始老是以ai为最后一位去算隔位差,结果导致不知道是+ai还是-ai,很纠结,最后瑞瑞说他是以ai为第一位开始算隔位差的,于是,问题得到解决,还是得多想想啊。

分享到:
评论

相关推荐

    HOJ.rar_HOJ_hoj2055_oj_绘图软件

    3. **学习算法应用**:可以看到排序、搜索、动态规划、图论等算法的实际应用。 4. **调试技巧**:通过查看错误案例的处理,学习如何定位和修复程序中的错误。 5. **提升编程能力**:参与ACM-OJ的题目通常需要高效和...

    HOJ_1001_Java

    【标题】"HOJ_1001_Java"指的是在Hit Online Judge(简称HOJ)平台上的一道编程题目,该题目使用Java语言进行解答。HOJ是一个在线编程竞赛平台,它提供了各种算法题目供参赛者用不同编程语言解决,以此来提升编程...

    HOJ_1003_Java

    【标题】"HOJ_1003_Java"指的是在Hit Online Judge(简称HOJ)平台上的一道编程题目,其对应的解决方案是用Java语言编写的。这道题目可能涉及了算法、数据结构或者特定的编程概念,是检验和提升编程能力的一个实践...

    hoj.rar_HOJ

    1. **掌握算法**:了解并实践各种经典的排序、搜索、图论、动态规划等算法。 2. **提高编程技巧**:学习如何编写高效、可读性强的代码。 3. **理解数据结构**:深入理解数组、链表、树、图等数据结构的使用场景和...

    hoj.rar_hoj杭州

    3. `2012(WA).cpp`: 可能是一个关于数据结构或动态规划的问题,错误可能在于未正确实现算法或者对输入数据的处理不当。 4. `2005(第几天WA).cpp`: 这个题目可能涉及到日期计算或日历问题,程序可能在处理闰年、月份...

    hoj小部分题

    【hoj小部分题】是针对HOJ(华中科技大学在线评测系统)中部分编程题目的集合,这些题目涵盖了不同的编程挑战,旨在帮助用户提升编程技能和算法理解。标签"hoj"表明这些题目来源于一个专门的编程竞赛或训练平台。...

    HOJ部分题目源代码

    3. **数值计算与数学技巧**:中国余数定理的运用,以及其他数学方法如动态规划、递推关系、矩阵快速幂等。 4. **编程语言特性**:C++、Java、Python等编程语言的特性和最佳实践,如模板类、函数重载、异常处理、...

    hit.rar_HIT-acm-HOJ-answer_算法 课件_课件

    这些资料可能会涵盖排序算法、搜索算法、图论算法、动态规划、贪心算法等核心内容,并且会讲解如何进行时间复杂度和空间复杂度的分析,如何优化算法效率,以及如何在实际编程项目中运用这些算法。 总的来说,这个...

    HOJ题目备份,值得拥有

    【标签】"HOJ题目"标识了这些文件与HOJ平台的编程题目相关,这可能是历次比赛、练习或挑战赛中的问题,涵盖了各种算法和编程知识领域,例如数据结构、图论、动态规划、排序算法等。 【压缩包子文件的文件名称列表】...

    hoj 离线题库 最新更新

    【标题】"hoj离线题库最新更新"所涉及的知识点主要集中在计算机科学与技术领域,特别是在线编程竞赛(Online Judge,简称OJ)的相关知识。hoj是众多在线编程竞赛平台之一,它提供了丰富的编程题目供用户进行训练和...

    HOj DP 分类 Zhouguyue

    根据提供的文件信息,可以推断出该列表主要涉及了一系列与**动态规划(Dynamic Programming,简称DP)**相关的编程题目。这些题目来自不同的问题集,覆盖了多个方面,如序列处理、游戏策略、路径寻找等。接下来,...

    HOJ1002:A+B+C

    注意数据范围,所以要用long long

    动态规划背包问题入门

    动态规划入门,hdu上的动态规划入门题的结题报告。 hdu 1171,hdu 1059,hdu 2159,hdu 2191,hdu 3496

    HOJ简单题400道源码

    acm简单题集,适合初学者交流,400道简单题

    hoj-judger:HydrogenOJ的简单沙箱和判断器

    GRUB_CMDLINE_LINUX="cgroup_enable=memory swapaccount=1"然后运行以下命令: update-grub && reboot在Node.js项目中安装要求:纱线yarn add hoj-judger自己建造要求:CMake 3.4或更高版本,g ++ 9或更高版本./...

    哈工大hoj1037

    哈工大hoj1037,详细的源代码,附有注释,可以看懂。

    c在线题库(hoj)

    c在线题库,希望大家下载 kjbjbk lnknn 你看了可能地方辅导书幅度不断说

    HOJ matrix 源代码

    采用暴力的思想,搜索所有可能路径。 int matrix[7][7]; int n; void inttoseries(int i,int *s) //将数i化为n进制的n位数 {int k,j; for(k=0,j=i;k;++k) {s[k]=j%n;j/=n;} } int maxcolumn(int *s)//每列最大和 ...

    六年级下册数学试题-期末测试卷-人教版(含答案) (1).doc

    这篇文档标题为“六年级下册数学试题-期末测试卷-人教版(含答案) (1).doc”,描述简短,没有提供具体知识点。标签为空,无法从中获取额外信息。文档部分内容显示了一些数学试题,其中包括选择题和可能的图像。 从...

    hoj2196 01背包.cpp

    01背包问题 #include #include #include #include #include using namespace std; int f[2700]; int w[600]; int val[600]; int main() { freopen("in","r",stdin); int t,tt,n,a,b; ... {

Global site tag (gtag.js) - Google Analytics