2

我试图实现将字符串传递给函数并返回包含有关该字符串的数据的结构的简单目标。我已经写了这个,但是当我尝试编译它时,我得到一个运行时错误,我不明白为什么。我很感谢你看一看。

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

struct stringStats
{
    int length;
    int uppercase;
    int lowercase;
    int digits;
    int nonAlphaNum;
};

struct stringStats stringReader (char anyString[])
{
    int i;
    struct stringStats returned = {0, 0, 0, 0, 0 };

    returned.length = strlen(anyString);

    for (i = 0; anyString[i] != '\0'; ++i)
    {
        if (isupper(anyString[i]))
            ++returned.uppercase;
        if (islower(anyString[i]))
            ++returned.lowercase;
        if (isdigit(anyString[i]))
            ++returned.digits;
        if (isalnum(anyString[i]) == 0)
            ++returned.nonAlphaNum;
    }
    return returned;
}

int main(void)
{
    struct stringStats stored;
    char passedString[] = "Th1s string's g0t it all!";
    stored = stringReader(passedString);
    printf ("%i\n%i\n%i\n%i\n%i\n", stored.length, stored.uppercase, stored.lowercase,
                                    stored.digits, stored.nonAlphaNum);

return 0;
}
4

3 回答 3

2

这是不正确的:

char passedString = "Th1s string's g0t it all!";

不确定这是如何编译的(建议在最高警告级别编译并将警告视为错误):

$ gcc -O2 -Wall -Werror -std=c99 -pedantic main.c -o main -pthread
main.c:在函数'main'中:
main.c:38:25:错误:初始化从指针生成整数而不进行强制转换 [-Werror]
main.c:39:5:错误:传递 'stringReader' 的参数 1 使指针从整数而不进行强制转换 [-Werror]
main.c:14:20:注意:预期为“char *”,但参数为“char”类型
cc1:所有警告都被视为错误

类型应该是char[]

char passedString[] = "Th1s string's g0t it all!";

请注意,返回类型是合法的,因为返回的是局部变量的副本(按值),而不是局部变量的地址。只是警告说,如果包含指针成员,则复制 astruct是危险的,因为现在两个s 具有指向相同地址的成员(悬空指针的潜在来源)。structstruct

本地struct确实需要初始化,因为它目前不是:

struct stringStats returned = {0}; /* All members initialized to zero. */

循环条件不正确,将for导致循环体永远不会被执行(第一次评估是0 != '\0'错误的)。改成:

for (i = 0; anyString[i]; ++i)
{
}
于 2013-04-05T10:33:37.223 回答
2

这里有几个问题。

  1. 在 main() 你有char passedString = "Th1s string's g0t it all!";- char 是存储一个字符,所以这应该是char *passedString = "Th1s string's g0t it all!";

  2. returned在增加成员之前,您没有初始化成员。

  3. 您的 for 循环的终止条件是检查i自身的值,而您实际上想要检查的值anyString[i]以在空字符上终止。

于 2013-04-05T10:39:04.993 回答
0

您正在将本地结构的值返回给调用对象。根据我的经验,只是传递引用并在内部执行操作更安全。

看看这个::

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

struct stringStats
{
    int length;
    int uppercase;
    int lowercase;
    int digits;
    int nonAlphaNum;
};

int stringReader (char anyString[], struct stringStats *returned)
{
    int i;
    returned->digits=0;
    returned->length=0;
    returned->lowercase=0;
    returned->nonAlphaNum=0;
    returned->uppercase=0;

    returned->length = strlen(anyString);

    for (i = 0; anyString[i] != '\0'; ++i)
    {
        if (isupper(anyString[i]))
            ++returned->uppercase;
        if (islower(anyString[i]))
            ++returned->lowercase;
        if (isdigit(anyString[i]))
            ++returned->digits;
        if (isalnum(anyString[i]) == 0)
            ++returned->nonAlphaNum;
    }
    return 0;
}

int main(void)
{
    struct stringStats stored;
    char passedString[] = "Th1s string's g0t it all!";
    stringReader(passedString,&stored);
    printf ("%i\n%i\n%i\n%i\n%i\n", stored.length, stored.uppercase, stored.lowercase,
                                    stored.digits, stored.nonAlphaNum);

    return 0;
}

这在我的末端编译并完美运行。希望这可以帮助!

于 2013-04-05T11:45:59.623 回答