繁体   English   中英

为什么 function 在第一次调用时跳过填充?

[英]why does the function skip the padding on the first call?

#include <iostream>
#include <cstring>
#include <cctype>

void go_lower(char *str);
void fill_str(char *mass);

int main()
{
    char str_1[80];
    char str_2[80];
    char *pointer_1;
    char *pointer_2;

    pointer_1 = str_1;
    pointer_2 = str_2;

    fill_str(pointer_1);

    fill_str(pointer_2);

    if(strcmp(str_1, str_2))
    {
        std::cout << "This strings are equal\n";
    }
    else
    {
        std::cout << "This strings are not equal\n";
    }


    return 0;
}

void fill_str(char *mass)
{
    std::cout << "Insert string to compare\n";
    while(*mass)
    {
        std::cin >> *mass;

        mass++;
    }
    std::cout << '\n';
}


void go_lower(char *str)
{
    while(*str)
    {
        if(isupper(*str))
        {
            *str = tolower(*str);
        }

        str++;
    }
}

不久前,我开始学习编程并尝试理解测试任务。 在这个程序中,无论字符的大小写如何,我都需要比较字符串。 当程序启动时,它直接填充 str_2 并且比较块得出字符串相等的结论。 错误是什么?

您的fill_str function 中的while (*mass)甚至不会循环一次,因为* mass可能在此处被初始化为0 (它实际上是未定义的行为,取决于您的编译器)。 因此,您的任何琴弦都不会被任何东西填满。

strcmp将您的字符串评估为相等,因为它们以这样一种方式初始化,它们从一开始就相等,并且由于上述原因而永远不会改变。

要读取字符串,请考虑使用getlinestd::cin如果您知道您的字符串不包含空格,例如。

std::cin >> mass;

在此处查看更多信息https://www.cplusplus.com/doc/tutorial/basic_io 还可以考虑使用std::string代替char arrays。

虽然在 C++ 中,您应该真正使用std::basic_string ,但您仍然需要知道如何处理普通的旧数组。 将普通旧数组传递给要填充的 function 时,您必须传递一个附加参数以将数组大小提供给 function。 在 function 中,您只能将size - 2字符读取到数组中(为nul 终止字符'\0' (ASCII 0 ) 保存索引size - 1

您还应该避免在代码中使用MagicNumbers 相反,如果您需要一个常量(例如80 ),#define 一个常量或在#define中使用一个const int 由于您可以选择返回类型,因此您应该返回读入每个字符串的字符数。 当您离开您的fill_str() function 并且没有理由必须调用 function 重新扫描字符串结尾时,该信息将可用。

您无法在尝试时有效地使用std::cin来读取 function 中的多字输入。 std::cin丢弃空格,因此您永远不会读取用户按[Enter]生成的'\n' 因此,您知道如何知道用户何时完成输入。 相反,您必须使用std::cin.get() 它将读取每个字符。

通过这些更改,您可以编写 function 以使用普通旧数组,如下所示:

#define MAXC 80     /* if you need a constant, #define one (or more) */
...
/* using plain-old-arrays, you must pass size of array */
size_t fill_str (char *mass, size_t size)
{
    size_t n = 0;   /* length counter */
    
    std::cout << "\nInsert string to compare\n";
    
    while (n < size - 1)                                /* read while array not full */
    {
        if ((*mass = std::cin.get()) && *mass != '\n')  /* use get() to read whitespace */
            n++;                    /* increment length counter */
        
        if (*mass == '\n')          /* if \n user pressed [Enter], input complete */
            break;
        
        mass++;                     /* increment pointer */
    }
    
    *mass = 0;                      /* nul-terminate when you leave read-loop */
    
    return n;                       /* return length */
}

您的示例,省略未使用的go_lower() function,则可能是:

#include <iostream>
#include <cstring>

#define MAXC 80     /* if you need a constant, #define one (or more) */

size_t fill_str (char *mass, size_t size);

int main (void)
{
    char str_1[MAXC];
    char str_2[MAXC];
    char *pointer_1;
    char *pointer_2;
    size_t len_1, len_2;

    pointer_1 = str_1;
    pointer_2 = str_2;

    len_1 = fill_str (pointer_1, MAXC);
    len_2 = fill_str (pointer_2, MAXC);
    
    if (len_1 != len_2) {
        std::cout << "\nstrings differ in length (" << 
                    len_1 << " != " << len_2 << ").\n";
        return 0;
    }
    
    if (strcmp (str_1, str_2) == 0)             /* only equal if return is 0 */
    {
        std::cout << "\nThis strings are equal\n";
    }
    else
    {
        std::cout << "\nThis strings are not equal\n";
    }

    return 0;
}

/* using plain-old-arrays, you must pass size of array */
size_t fill_str (char *mass, size_t size)
{
    size_t n = 0;   /* length counter */
    
    std::cout << "\nInsert string to compare\n";
    
    while (n < size - 1)                                /* read while array not full */
    {
        if ((*mass = std::cin.get()) && *mass != '\n')  /* use get() to read whitespace */
            n++;                    /* increment length counter */
        
        if (*mass == '\n')          /* if \n user pressed [Enter], input complete */
            break;
        
        mass++;                     /* increment pointer */
    }
    
    *mass = 0;                      /* nul-terminate when you leave read-loop */
    
    return n;                       /* return length */
}

示例使用/输出

$ ./bin/golower

Insert string to compare
apples and bananas

Insert string to compare
apples and bananas

This strings are equal

$ ./bin/golower

Insert string to compare
pickle

Insert string to compare
pickles

strings differ in length (6 != 7).

如开头所述,您确实应该使用std::stringgetline()来读取用户输入,但您也应该熟悉普通旧数组。 看看事情,如果你有问题,请告诉我。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM