c - 为什么 fgets 不输入第一个值?

标签 c input io output fgets

我正在编写一个程序来快速编写我的 html 文件。当我开始写我的页面内容时,我遇到了问题。

#include<stdio.h>

int main()
{
int track;
int question_no;

printf("\nHow many questions?\t");

scanf("%d",&question_no);

char question[question_no][100];

    for(track=1;track<=question_no;track++)
    {
        printf("\n<div class=\"question\">%d. ",track);
        printf("\nQuestion number %d.\t",track);
        fgets(question[track-1],sizeof(question[track-1]),stdin);
        printf("\n\n\tQ%d. %s </div>",track,question[track-1]);
    }

}

在这个程序中,我正在写一些问题及其答案(在 html 文件中)。当我测试运行这个程序时,我将 question_no 的值输入到 3。但是当我输入我的第一个问题时,它没有进入 question[0],因此第一个问题不输出。其余问题输入无问题。

我在 stackoverflow 上搜索了一些问题,发现 fgets() 寻找最后一个 \0 字符,而 \0 停止了它。< br/> 我还发现我应该使用 buffer 通过 fgets() 很好地输入所以我使用了:setvbufsetbuf但这也没有用(我可能编码错误)。我还在第一个和最后一个(也是)scanf 语句之后使用了 fflush(stdin) 从 stdin 中删除任何 \0 字符,但这也没用。

有没有办法接受fgets()的第一个输入?
我现在正在使用标准输入和标准输出。我没有访问、读取或写入任何文件。

最佳答案

第一个提示也使用 fgets。您还应该 malloc 您的数组,因为您不知道它在编译时要多长时间。

#include <stdlib.h>
#include <stdio.h>

#define BUFSIZE 8

int main()
{
    int track, i;
    int question_no;
    char buffer[BUFSIZE], **question;

    printf("\nHow many questions?\t");

    fgets(buffer, BUFSIZE, stdin);
    question_no = strtol(buffer, NULL, 10);

    question = malloc(question_no * sizeof (char*));
    if (question == NULL) {
        return EXIT_FAILURE;
    }
    for (i = 0; i < question_no; ++i) {
        question[i] = malloc(100 * sizeof (char));
        if (question[i] == NULL) {
            return EXIT_FAILURE;
        }
    }

    for(track=1;track<=question_no;track++)
    {
        printf("\n<div class=\"question\">%d. ",track);
        printf("\nQuestion number %d.\t",track);
        fgets(question[track-1],100,stdin);
        printf("\n\n\tQ%d. %s </div>",track,question[track-1]);
    }

    for (i = 0; i < question_no; ++i) free(question[i]);
    free(question);
    return EXIT_SUCCESS;
}

C 中的二维数组

type 的二维数组可以由指向 type 的指针数组表示,或者等效地 type**(指向指向的指针的指针类型)。这需要两个步骤。

char **question 为例:

第一步是分配一个char*数组。 malloc 返回一个指向它分配的内存开始的指针,如果失败则返回 NULL。所以检查question是否为NULL

其次是让每个 char* 都指向它们自己的 char 数组。因此,for 循环为 question 的每个元素分配了一个大小为 100 个 char 的数组。同样,这些 malloc 中的每一个都可能返回 NULL,因此您应该检查一下。

每个 malloc 都应该有一个 free,所以当您使用完分配的内存后,您应该反向执行该过程。

malloc reference

结构

long int strtol(const char *str, char **endptr, int base);

strtol 返回一个 long int(在上面的代码中被转换为一个 int)。它将 str 分成三部分:

  1. 字符串数字内容之前的任何空格
  2. 它识别为数字的部分,它将尝试转换
  3. 字符串的其余部分

如果endptr 不是NULL,它将指向第三部分,所以您知道strtol 在哪里完成。你可以这样使用它:

#include <stdio.h>                                                                                                                             
#include <stdlib.h>                                                                                                                            

int main()                                                                                                                                     
{                                                                                                                                              
    char * endptr = NULL, *str = "    123some more stuff";                                                                                       
    int number = strtol(str, &endptr, 10);                                                                                                       
    printf("number interpreted as %d\n"                                                                                                          
           "rest of string: %s\n", number, endptr);                                                                                              
    return EXIT_SUCCESS;                                                                                                                         
}

输出:

number interpreted as 123
rest of string: some more stuff

strtol reference

关于c - 为什么 fgets 不输入第一个值?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/20092468/

相关文章:

c++ - 函数指针到底指向哪里?

c - 定义一个矩阵并将其传递给 C 中的函数

c++ - 尝试了解输入验证循环

android - 在android中反序列化对象时出现StackOverFlowError

c++ - 将结构传递给 dll

python - 通过套接字传输大文件

javascript - 根据内容动态调整 HTML 文本输入宽度

c - fgets 打印出 'à' 而不是实际输入

haskell - 为什么这不能在恒定内存中运行?

linux - 为什么 MongoDB 在 Debian 上比在 Windows 上慢..?