簡體   English   中英

如何確定使用fgets()讀取的字符數?

[英]How to determine number of characters that were read with fgets()?

這是手冊頁中fgets()的描述:

char *fgets(char *s, int size, FILE *stream);
...

RETURN VALUE
  fgets() returns s on success, and NULL on error or  when  end  of  file
  occurs while no characters have been read.

它不遵循read模式,如果失敗,則返回-1;如果成功,則返回讀取的字節數。 而是返回一個char* ,如果失敗,則為NULL ;如果成功,則為s 這不會給我有關輸入時間長度的任何信息。 所以,如果我有這樣的事情:

char input_buffer[256];
fgets(input_buffer, sizeof(input_buffer), stdin);

fgets調用之后,有什么方法可以告訴輸入多長時間沒有對緩沖區進行零初始化?

謝謝。

如何確定使用fgets()讀取的字符數?

char *fgets(char *s, int size, FILE *stream);

檢查fgets()返回值后,使用strlen(s)

if (fgets(s, size, stream)) {
  printf("number of characters that were read: %zu\n", strlen(s));
} else if (feof(stream)) {
  printf("number of characters that were read:0 End-of-file\n");
} else  {
  printf("number of characters that were read unknown due to input error\n");
}

除非讀取了空字符 '\\0' 否則它將起作用因為strlen()將在函數附加的字符之前遇到'\\0' 在這種情況下, fgets()之后的strlen(s) fgets()將報告較小的值。

有多種技巧可以預填充s ,然后調用fgets() ,但尚不確定其余未讀緩沖區發生了什么。 還存在其他缺點。

如果需要考慮將空字符作為有效輸入流的一部分,請使用fgetc()或類似getline()東西。


空字符是文本的一種常見情況是將文本編碼為UTF-16。 當然,代碼不應使用fgets()來讀取該文本,但這需要先驗知識。 由於錯誤地認為文本文件是非空字符文本文件,因此許多讀取文本的代碼都以神秘的方式失敗了。

此外,即使文本文件缺少空字符 ,下面的代碼也會發生什么?

if (fgets(s, size, stream)) {
  size_t len = strlen(s);
  s[--len] = '\0';  // poor way to lop off the trailing \n, this could be UB
}

此類代碼利用黑客利用方式引發了未定義的行為 :在該的開頭插入文件中的空字符 (見這個這個更好的解決方案,以割斷潛在\\n

健壯的代碼不能假定文本格式正確,並會采取措施來檢測異常。


書呆子注意: fgets(char *s, int size, FILE *stream);有一些病理問題fgets(char *s, int size, FILE *stream); size < 2

就在這里。 如果成功,它始終為null終止。 因此它將是strlen(buf)

從標准7.21.7.2

char *fgets(char * restrict s, int n,FILE * restrict stream); fgets函數從stream指向的stream s指向的數組中讀取的字符數最多少於n指定的字符數。 在換行符(保留)或文件結束之后,不會讀取其他字符。 在將最后一個字符讀入數組后,立即寫入空字符。

暫無
暫無

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

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