【问题标题】:Issue finding number of occurrences of a given substring in a string问题查找字符串中给定子字符串的出现次数
【发布时间】:2016-01-27 14:00:16
【问题描述】:

下面的代码总是返回匹配子字符串的数量为零。代码中没有错误,我不确定我在逻辑上哪里出错了。

#include<stdio.h>
#include<string.h>

int main()
{ 
    int i,j,len ,k ,count, num ;
    char str[100],sub[100],comp[100] ; 
    // sub is the sub string .
    printf("Please enter the string") ; 
    gets(str) ;
    printf("Enter the substring to be searched for") ;
    gets(sub) ;
    len=strlen(sub) ;
    for ( i=0 ; i < strlen(str) - len ; i++ ) 
    //Goes till length of string - length of sub string so that all characters can be compared.
      {  
         num = i + len ;
         for ( j=i,k=0 ; j<num ; j++, k++ )
         //Loop to store each sub string in an array comp.
           {
             comp[k]=str[j] ;
           }
         if ( strcmp(comp,sub) == 0 )
            { count++ ; }
     }
    printf("no of occurances is:%d",count) ;
    return 0 ;
}  

【问题讨论】:

  • 这段代码没有任何意义。为什么首先需要复制子字符串?
  • 除非有很好的理由,否则使用 fgets 而不是 gets。
  • 使用调试器或至少打印您检查的数据。
  • @ForeverStudent:哪个原因会纠正使用没有更多功能的不安全功能?
  • @Olaf:我们以前都听过的愚蠢的:赋值不允许 fgets,我们的自定义编译器/运行时不支持 fgets,等等

标签: c arrays string loops


【解决方案1】:

如 cmets 中所述,在构造 comp 时,您不会在末尾添加终止空字节。因为comp 的其余部分未初始化,所以在调用strcmp 时会调用未定义的行为。

for 内部循环的末尾添加空字节将解决问题:

     for ( j=i,k=0 ; j<num ; j++, k++ )
     //Loop to store each sub string in an array comp.
       {
         comp[k]=str[j] ;
       }
     comp[k] = '\0';

其实与其创建单独的子字符串,不如使用strncmp,它最多比较一定数量的字符:

for ( i=0 ; i < strlen(str) - len ; i++ ) 
//Goes till length of string - length of sub string so that all characters can be compared.
  {  
     if ( strncmp(&str[i],sub,strlen(sub)) == 0 )
        { count++ ; }
 }

另外,不要使用gets,因为这很容易导致缓冲区溢出。请改用fgets

【讨论】:

  • 注意:由于比较不会超过字符串的长度,代码代码使用memcmp(&amp;str[i], sub, ...)可能会更快与长字符串YMMV。
  • 这对像我这样的初学者非常有帮助。谢谢!
  • @RahulMayuranath 很高兴我能帮上忙。如果您觉得有用,请随时 accept this answer
  • 在进行上述更改后(使用 fgets 而不是 get 并添加一个 terimal 空字节),现在每个测试用例的输出数字都超过 30000。发生了什么?
  • @RahulMayuranath 我们需要查看代码。请将其作为一个单独的问题发布。
【解决方案2】:
  • 尝试从此更改您的 for 循环:

    for ( i=0 ; i < strlen(str) - len ; i++ ) 
    

    for ( i=0 ; i <= strlen(str) - len ; i++ ) 
    

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2023-03-13
    • 2010-12-25
    • 1970-01-01
    • 2015-01-28
    • 1970-01-01
    • 2021-01-11
    • 2012-12-26
    相关资源
    最近更新 更多