【问题标题】:Does a string contains a word from a list字符串是否包含列表中的单词
【发布时间】:2026-02-08 22:15:01
【问题描述】:

我有一个字符串和一个关键字数组。如果字符串包含列表中的关键字之一,我想检查该关键字是否是该字符串的唯一元素。如果不是,我想返回一个错误。最后一件事,字符串总是以 \n 结尾。

我的关键字数组如下:

const char * keywordsTable[] = 
    {
    "INIT",
    "BEGIN",
    "END",
    "ROUTINES",
    "ENDROUTINES",
    "ENDWHEN",
    "WHEN",
    "WHILE"
    };

例如,如果我的字符串是"BEGIN\n",那么一切都很好。如果我的字符串是"BEGIN FOO\n""FOO BEGIN\n",我必须返回一个错误。最后,如果我的字符串是"BEGINFOO\n",一切都很好。 (错误码为1,否则为0)

我尝试了一些方法(我不知道如何进行):

int CheckKeyword(char * str)    
    {
    int nKeywords = sizeof(keywordsTable) / sizeof(keywordsTable[0]);
    char * strTok = NULL;
    char * keywrdWithLF = malloc(20);
    // I don't want to check for the last two keywords nor the first
    for (int i = 1; i < nKeywords - 2; i++)
        {
        strcpy_s(keywrdWithLF, 20, keywordsTable[i]);
        strcat_s(keywrdWithLF, 20, "\n");
        strTok = strstr(str, keywrdWithLF);
        // If my string contains a keyword
        if (strTok != NULL)
            {
            // If the string contains other characters... and I'm stuck
            if (strcmp(str, keywrdWithLF))
                {
                }
            else
                {
                free(keywrdWithLF);
                return 1;
                }   
            }           
        }
    free(keywrdWithLF);
    return 0;
    }

提前谢谢你(请不要抱怨我的缩进样式,我必须使用 Whitesmith 缩进)!

【问题讨论】:

  • 好的,这里的问题是什么?
  • 我写了我卡在代码里的地方
  • “我被卡住了”不是问题。究竟是什么问题?
  • 我只是不知道如何继续......我会在问题中准确说明
  • 在任何情况下它都比 strcpy() 更安全,并且可以更好地处理错误。无论如何,这不是我的问题

标签: c string substring


【解决方案1】:
int CheckKeyword(char * str)    
    {
    int nKeywords = sizeof(keywordsTable) / sizeof(keywordsTable[0]);
    char * strTok = NULL;
    for (int i = 1; i < nKeywords - 2; i++)
        {
        if(NULL!=(strTok = strstr(str, keywordsTable[i])))
            {
            int len = strlen(keywordsTable[i]);
            if(strTok == str)
                {
                if(str[len]==' ' || str[len]=='\t')
                return 1;
                }
            else
                {
                if((strTok[-1]==' ' || strTok[-1]=='\t') && isspace(strTok[len]))//isspace in <ctype.h>
                return 1;
                }
            }
        }
    return 0;
    }

【讨论】:

  • 非常感谢,代码清晰简洁,按预期工作!
【解决方案2】:

也许是另一种方法?

int CheckKeyword(char * str)    
   {
   int rCode=0;
   int nKeywords = sizeof(keywordsTable) / sizeof(keywordsTable[0]);
   char *keyword;
   char *cp = keywordsTable;

我假设由于 str 被定义为“char * str”而不是“const char * str”,因此可以修改输入字符串。因此,为什么不直接从等式中消除“\n”问题呢?

   /* Elininate the newline character from the end of the string. */
   if((cp = strchr(str, '\n'))
      *cp = \0;

   // I don't want to check for the last two keywords nor the first.
   nKeywords -= 3;
   ++keyword;

   /* Loop through the keywords. */
   while(nKeywords)
      {
      // "I want to check if the keyword is the only element of this string." 
      // "If it's not, I want to return an error."
      if((cp=strstr(str, keyword))
         {
         /* Check for stuff prior to the keyword. */
         if(cp != str)
            rCode=1;

         /* Check for stuff after the keyword. */
         // Finally if my string is "BEGINFOO\n", everything is fine.
         if(' ' == str[strlen[keyword])
            rCode=1;

         if(strcmp(cp, keyword))
            rCode=1

         break;
         }

      ++keyword;
      --nKeywords;
      }

   return(rCode);
   }

【讨论】:

  • 感谢这段代码,但我忘了放 const 因为我无法修改 str 值。因此,使用您的解决方案,我必须制作一个 memcpy,而其他给定的代码效率更高(感谢您使用相同的缩进样式):)
最近更新 更多