比较字符串的结尾

comparing the ending of the strings

我正在编写一个程序来比较不同的字符串。特别是以 OH 结尾的化学元素。如果字符串以 OH 结尾,我必须 return -1。但是,我的程序不起作用。我哪里错了?

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

int hydroxide(char *string);

int main() {
    char *string;
    printf("Enter String:");
    gets(string);
    printf("%d", hydroxide(string));
}

int hydroxide(char *string) {
    string = strrchr(string, 'O');
    if (string != NULL)
        return (strcmp(string, "OH"));
    return (-1);
 }

获取字符串的长度并检查最后两个字符。

int len = strlen(string);
      if(string[len-1] == 'H' && string[len-2] =='O')
          return -1;

对于初学者来说,函数的逻辑是错误的。

通常这样的函数应该return1(或者正值)对应逻辑true或者0对应逻辑false 当它回答像 "yes or no".

这样的问题时

这次通话

strcmp(string, "OH")

returns 如果两个字符串相等则为 0。否则,函数可以 return 任何正值或负值,具体取决于第一个字符串是大于还是小于第二个字符串。

除此之外,函数参数应具有限定符 const,因为传递的字符串在函数内不会更改。

您没有保留要读取字符串的内存。声明的指针

char *string;

未初始化且具有不确定的值。因此这个调用

gets(string);

调用未定义的行为。

请注意函数 gets 是一个不安全的函数,C 标准不支持它。相反,您应该使用标准 C 函数 fgets.

而且如果功能再通用一点就更好了。那是它可以检查任何提供的字符串后缀的时候。始终尝试编写更通用的函数。在这种情况下,它们可以重复使用。

下面有一个演示程序,展示了如何定义函数。

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

int hydroxide( const char *s, const char *suffix )
{
    size_t n1 = strlen( s );
    size_t n2 = strlen( suffix );

    return !( n1 < n2 ) && strcmp( s + n1 - n2, suffix )  == 0;
 }

int main(void) 
{
    enum { N = 100 };
    char s[N];

    while ( 1 )
    {
        printf( "Enter a String (empty string - exit): " );

        if ( fgets( s, N, stdin ) == NULL || s[0] == '\n' ) break;

        s[ strcspn( s, "\n" ) ] = '[=13=]';

        printf( "%s\n", hydroxide( s, "OH" ) ? "true" : "false" );
    }

    return 0;
}

程序输出可能看起来像

Enter a String (empty string - exit): brogrammerOH
true
Enter a String (empty string - exit): 

你的函数太复杂了,如果后缀是OH就returns0。一种更简单的方法是计算字符串的长度,如果该长度至少为 2,则将最后 2 个字符与 'O''H':

进行比较
int hydroxide(const char *string) {
    size_t len = strlen(string);
    if (len >= 2 && string[len - 2] == 'O'  && string[len - 1] == 'H')
        return -1;
    else
        return 0;
}

此外,main 函数有未定义的行为:string 是一个未初始化的 char 指针:将它传递给 gets() 将在 [=19= 时导致未定义的行为] 尝试向其写入字节。另请注意,gets() 已过时并已从最新版本的 C 标准中删除,因为对于足够长的输入字符串,无法防止缓冲区溢出。使用 fgets() 代替并删除尾随换行符(如果有):

这是修改后的版本:

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

int hydroxide(const char *string) {
    size_t len = strlen(string);
    if (len >= 2 && string[len - 2] == 'O'  && string[len - 1] == 'H')
        return -1;
    else
        return 0;
}

int main() {
    char buf[80];
    printf("Enter String: ");
    if (fgets(buf, sizeof buf, stdin)) {
        buf[strcspn(buf, "\n")] = '[=11=]';  // strip the newline if any
        printf("%d\n", hydroxide(string));
    }
    return 0;
}