创建strchr()的简化版本

use*_*260 9 c

试图创建一个简单的函数,在字符串中查找单个字符"就像strchr()会",我做了以下内容:

char* findchar(char* str, char c)
{
    char* position = NULL;
    int i = 0;
    for(i = 0; str[i]!='\0';i++)
    {
        if(str[i] == c)
        {
            position = &str[i];
            break;
        }
    }
    return position;
}
Run Code Online (Sandbox Code Playgroud)

到目前为止它的作用.但是,当我看到strchr()的原型时:

char *strchr(const char *str, int c);
Run Code Online (Sandbox Code Playgroud)

第二个参数是int?我很想知道..为什么不是炭?这是否意味着我们可以像使用char一样使用int来存储字符?

这让我想到第二个问题,我试图改变我的函数接受一个int作为第二个参数......但我不确定这样做是否正确和安全:

char* findchar(char* str, int c)
{
    char* position = NULL;
    int i = 0;
    for(i = 0; str[i]!='\0';i++)
    {
        if(str[i] == c) //Specifically, is this line correct? Can we test an int against a char? 
        {
            position = &str[i];
            break;
        }
    }
    return position;
}
Run Code Online (Sandbox Code Playgroud)

Rol*_*lig 6

在ANSI C89之前,声明的函数没有原型.当时的声明strchr看起来像这样:

char *strchr();
Run Code Online (Sandbox Code Playgroud)

而已.根本没有声明参数.相反,有这些简单的规则:

  • 所有指针都作为参数传递
  • int转换为的范围更小的所有整数值int
  • 所有浮点值都将转换为 double

所以当你打电话时strchr,真正发生的是:

strchr(str, (int)chr);
Run Code Online (Sandbox Code Playgroud)

引入ANSI C89时,必须保持向后兼容性.因此它将原型定义strchr为:

char *strchr(const char *str, int chr);
Run Code Online (Sandbox Code Playgroud)

这样可以保留上述示例调用的确切行为,包括转换为int.这很重要,因为实现可能会定义传递char参数的工作方式与传递int参数不同,这在8位平台上是有意义的.

  • 你有这方面的资料吗?在C理由中没有提到它. (2认同)

chu*_*ica 5

考虑fgetc()范围中的值的返回值,unsigned char以及EOF一些负值.这是传递给的价值strchr().

@Roland Illig公司介绍,导致保留使用历史的一个很好的解释int chstrchr().


OP的代码失败/有如下问题.

1)按照§7.23.1.13进行char* str处理unsigned char *str

对于本子条款中的所有函数,每个字符都应被解释为具有unsigned char类型

2)i应该是type size_t,来处理整个字符数组的范围.

3)出于此目的strchr(),空字符被视为搜索的一部分.

终止空字符被认为是字符串的一部分.

4)更好地使用,const因为str没有改变.

char* findchar(const char* str, int c)     {
    const char* position = NULL;
    size_t i = 0;
    for(i = 0; ;i++) {
        if((unsigned char) str[i] == c) {
            position = &str[i];
            break;
        }
        if (str[i]=='\0') break;
    }
    return (char *) position;
}
Run Code Online (Sandbox Code Playgroud)

更多细节

strchr函数定位指向的字符串中的第一次出现c(转换为a char)s.C11dr§7.23.5.22

所以int c就像对待一样char.这可能意味着

        if((unsigned char) str[i] == (char) c) {
Run Code Online (Sandbox Code Playgroud)

但我认为这意味着:

        if((unsigned char) str[i] == (unsigned char)(char) c) {
Run Code Online (Sandbox Code Playgroud)

或者干脆

        if((unsigned char) str[i] == (unsigned char)c) {
Run Code Online (Sandbox Code Playgroud)