簡體   English   中英

為什么整數不能從 C 中的文件打印

[英]Why wont the integers print from a file in C

我用 C 編寫了一個簡單的程序來從文件中讀取整數,並將整數打印到stdout 代碼可以編譯,但不會打印出我在不同文件中編寫的整數。 這是我寫的:

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

int main(int argc, char *argv[]) {
    FILE *fp = fopen(argv[0], "r");
    int x = 0;
    int nums[1024];
    int num;

    while (fscanf(fp, "%d", &num) == 1) {
        nums[x] = num;
        x++;
    }

    printf("Here are your numbers");

    int i = 0;

    while (nums[i] != '\0') {
        printf("%d\n", nums[i]);
        i++;
    }

    fclose(fp);
    exit(0);
}

我只是想打印用fp寫的整數

你的代碼有很多問題。 首先是錯字: nums已聲明,但變量是num

argv[0]不是程序的第一個參數,它是程序的名稱(產生程序的execv調用的第一個參數)。 程序的第一個參數是argv[1] 您必須檢查argv[1]存在以及文件是否成功打開。

  if( argc <= 1 ) {
      fprintf(stderr, "Usage: %s <filename>\n", argv[0]);
      return -1;
  }

  FILE *fp = fopen(argv[1], "r");
  if( fp == NULL ) {
      fprintf(stderr, "Could not open %s for reading\n", argv[1]);
      return -1;
  }

然后是如何確定數組中有多少個數字的問題。 您使用的技術適用於以空字符結尾的字符串(字符數組)或指針數組,但對於整數數組nums[i] != '\\0'nums[i] != 0你可能會讀到數字零。 所以你不能在整數數組上使用這種邊界技術。 (你也忘了在數字閱讀結束時設置邊界)

相反,您已經有x跟蹤您讀入的數字數量。使用它。 我已將其重命名為更具描述性的num_nums 我還使用了for循環來使帶有遞增計數器的循環更清晰。

  int num_nums = 0;
  int nums[1024];
  int num;

  for( num_nums = 0; fscanf(fp, "%d", &num) == 1; num_nums++ ) {
    nums[num_nums] = num;
  }

  printf("Here are your numbers.\n");

  for( int i = 0; i < num_nums; i++ ) {
    printf("%d\n", nums[i]);
  }

最后一個問題是使用固定大小的數組來處理輸入。 固定大小的緩沖區和輸入是一個等待發生的安全漏洞。 您應該將輸入限制為緩沖區的大小(即 1024 個數字),或者更好的是,使用自動增長的數組。 這種類型的數組通常是一個結構體,它也為您跟蹤其大小。

與其實施一個,我鼓勵您使用提供改進數據結構的眾多庫之一,例如Gnome Lib

首先, argv[0]是程序名。 我想你的意思是argv[1] ,它是第一個命令行參數,不包括程序名稱。 然后,檢查fopen的返回值。 如果為NULL ,則無法打開文件。 修改后的代碼是

int main(char *argv[], int argc)
{
    FILE *fp;
    int i;

    if ((fp = fopen(argv[1], "r")) != NULL) {
        while (fscanf(fp, "%d", &i) > 0)
            printf("%d\n", i);
    } else /* could not open file; print reason */
        perror("fopen");

    fclose(fp);
    return 0;
}

除了@stackptr在他的回答中所說的......

while(nums[i] != '\0'){

不是循環從文件中讀取的數字的正確方法。 nums的元素未初始化超出從磁盤讀取的內容。 因此,將它們的值與'\\0'進行比較是導致未定義行為的原因。

您可以使用:

// x is the number of ints read into nums.
for ( i = 0; i < x; ++i )
{
   printf("%d\n", nums[i]);
}
  1. 您正在嘗試使用argv[0]讀取可執行文件本身。 雖然它沒有任何問題,但是文件的開頭與"%d"說明符所期望的不匹配,因此循環將終止,因為您有一個條件,即它必須在每次迭代中讀取一個條目,直到無法讀取任何條目. 因此x將是'\\0'

  2. 即使您使用了argv[1]並傳入了一些包含例如1 2 3文件,這也將是一場災難。 這是因為您正在從數組nums打印,直到它的第i個條目不是'\\0' 您從未將nums設置為'\\0' ,並且nums是一個自動(局部)變量。 因此,您的程序將具有未定義的行為。 要理解我在說什么,請嘗試將nums所有元素初始化為5 ,然后使用包含上述示例的文件運行程序。 因此將循環更改為while (i < x) { /* print your nums[i] and increment i */ }

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM