zoukankan      html  css  js  c++  java
  • UVa455 Periodic String 的wronganswer问题探讨,以及AC的新思路

    题目的意思是一个字符串有某个长度为k的字符串通过不断重复形成的,而k被称为该字符串的周期。而我们所要做的是找出该字符串的最小周期。

    input

    The first line is an integer T,That means there are have T test cases; the following T lines are T strings;

    output

    Each line is an answer,and there a blank line between two answers.

    (具体的题目描述请参考原题)

    分析:在开始看到这个题目的时候,第一个想到的是从第一个字符开始找,开始假设最小周期min=1;只要对string进行一次遍历,并且在遍历的过程中,以min的间隔分别和字符串开头的min个字符进行比较,如果出现不相同,比如恰巧遍历到j位置,那么min就转化为j+1;启发源于:abcabcabcadcab,在d位置出现了不同,那么min=11;于是便得出了下面的代码:

    #include<stdio.h>
    #include<string.h>
    int main()
    {
    int T;
    char s[81];
    int min,t,j,flag;
    scanf("%d",&T);
    //printf(" ");
    for(int i=0;i<T;i++)
    {
    scanf("%s",s);
    int l = strlen(s);
    min=1;
    for(j=1;j<l;j++)
    {

    t=j;

    for(int k=0;k<min;k++)
    {
    if(t+k<l)
    {

    j=t+k;
    if(s[k]!=s[j])
    {
    flag=0;
    break;
    }
    }
    }
    t=t+min;
    if(flag==0)
    {
    break;
    }
    }
    if(flag==1)
    {
    break;
    }

    if(min>l/2)
    {
    min=l;
    break;
    }
    }
    }
    if(i==T-1)
    printf("%d ",min);
    else
    printf("%d ",min);
    }
    return 0;
    }

    在一开始,觉得这个思路应该是比较正确的,不会有什么不妥,然而提交的结果是Wronganswer,尽管后期对细节进行了处理,比如周期超过l/2则周期为l;但是都没有通过。

    因为wweewwwweeww,这个字符串用上面的思路是绝对行不通的。因此可以肯定上面的wronganswer是思路上错了。

    那么可以确保正确的思路又是怎么样的呢?

    1.比较明显的特点,周期min必定是strlen(s)的因子,而且是最小的,因此利用一个循环从小到大对strlen(s)的因子进行判定是否符合条件即可,其中需要花些心思的是如何进行判定周期是符合条件的。其实,只要将之后的每一段和第一段进行比较或者在之后的每一段的每个字符进行比较,第一个循环为每个字符的循环,嵌套一个是否相等的循环,用一个flag进行标记,方便外循环的break,因为只要有内循环出现不相等,则外循环之后都不需要进行比较了。

    代码应该表较容易写出来。

    2.是在第一种思路上和错误的思路相结合的方式。每个循环,其第一个字符必定和s[0],是相等的,因此只要再加上s[j]==s[0]&&l%j==0可以个快速的进行判定。

    具体代码如下:

    #include<stdio.h>
    #include<string.h>
    int main()
    {
    int T;
    char s[81];
    int min,t,j,flag;
    scanf("%d",&T);
    //printf(" ");
    for(int i=0;i<T;i++)
    {
    scanf("%s",s);
    int l = strlen(s);
    min=1;
    for(j=1;j<l;j++)
    {
    if(s[j]==s[0]&&l%j==0)
    {
    min=j;
    t=j;
    //printf("%d",min);

    while(t<=l-min)
    {
    flag=1;
    for(int k=0;k<min;k++)
    {
    if(t+k<l)
    {
    if(s[k]!=s[t+k])
    {
    flag=0;
    break;
    }
    }
    }
    t=t+min;
    if(flag==0)
    {
    break;
    }
    }
    if(flag==1)
    {
    break;
    }

    if(min>l/2)
    {
    min=l;
    break;
    }
    }
    }
    if(j>=l)
    {
    min=l;
    }
    if(i==T-1)
    printf("%d ",min);
    else
    printf("%d ",min);
    }
    return 0;
    }

    最后,只得一说的是原题在INPUT的内容里加上了T...followed by a blank line,其实并没有起到任何作用,别管就是。在输出时也要注意下输出格式题目就可以解决了。

    敢于面对难题,敢于面对自己。
  • 相关阅读:
    【华磊随笔】一个企业的内部讨论(含高层)“30岁IT人,产出代码还是产出思想”之我见。
    dotNetGrid 演示站点(new)争取做ASP.NET中最好的Ajax开源表格控件
    【华磊随笔】进一步的分析:开发者版本;你属于哪个版本的程序员?
    新增格式化单元格数据功能dotNetFlexGrid1.24,快速的设置您的表格数据的不同样式;现在开始扔掉你的Asp.net GridView吧。(更新FieldFormatorHandle参数)
    【华磊随笔】技术到底值不值钱,到底值多少钱有感于公司新产品的上线
    【华磊原创】某企业前两年的开发人员技术能力评估表(不分语言)相对比较全面也比较细
    【华磊原创】安装程序自动检测安装.Net Framework运行环境(使用InnoSetup)
    mainline.js主线
    JS中的“!!”
    读“周大师代码评审”有感
  • 原文地址:https://www.cnblogs.com/cittysteven/p/7190516.html
Copyright © 2011-2022 走看看