名稱空間
變體
操作

std::ungetc

來自 cppreference.com
< cpp‎ | io‎ | c
 
 
 
 
定義於標頭檔案 <cstdio>
int ungetc( int ch, std::FILE *stream );

如果 ch 不等於 EOF,則將字元 ch(重新解釋為 unsigned char)壓入與流 stream 相關聯的輸入緩衝區,以便後續從 stream 讀取操作將檢索到該字元。與流相關聯的外部裝置未被修改。

流重定位操作 std::fseekstd::fsetposstd::rewind 會丟棄 ungetc 的效果。

如果 ungetc 在沒有 intervening 讀取或重定位的情況下被多次呼叫,它可能會失敗(換句話說,保證大小為 1 的回推緩衝區,但任何更大的緩衝區都是實現定義的)。如果執行了多次成功的 ungetc,讀取操作將按 ungetc 的相反順序檢索回推的字元。

如果 ch 等於 EOF,則操作失敗且流不受影響。

成功呼叫 ungetc 會清除檔案結束狀態標誌 std::feof

成功呼叫 ungetc 在二進位制流上會將流位置指示器減一(如果流位置指示器為零,則行為不確定)。

成功呼叫 ungetc 在文字流上會以未指定的方式修改流位置指示器,但保證在所有回推字元透過讀取操作檢索後,流位置指示器等於其在 ungetc 之前的值。

目錄

[編輯] 引數

ch - 要推入輸入流緩衝區的字元
stream - 要將字元推回的檔案流

[編輯] 返回值

成功時返回 ch

失敗時返回 EOF,並且給定的流保持不變。

[編輯] 注意

回推緩衝區的大小在實踐中從 4k(Linux、MacOS)到小至 4(Solaris)或保證的最小 1(HPUX、AIX)不等。

如果回推的字元等於外部字元序列中該位置存在的字元,則回推緩衝區的表觀大小可能更大(實現可能只需遞減讀取檔案位置指示器並避免維護回推緩衝區)。

[編輯] 示例

演示 std::ungetc 的原始用途:實現 std::scanf

#include <cctype>
#include <cstdio>
 
void demo_scanf(const char* fmt, std::FILE* s)
{
    while (*fmt != '\0') {
        if (*fmt == '%') {
            switch (*++fmt) {
                case 'u': {
                    int c{};
                    while (std::isspace(c=std::getc(s))) {}
                    unsigned int num{};
                    while (std::isdigit(c)) {
                        num = num*10 + c-'0';
                        c = std::getc(s);
                    }
                    std::printf("%%u scanned %u\n", num);
                    std::ungetc(c, s);
                    break;
                }
                case 'c': {
                    int c = std::getc(s);
                    std::printf("%%c scanned '%c'\n", c);
                    break;
                }
            }
        } else {
            ++fmt;
        }
    }
}
 
int main()
{
    if (std::FILE* f = std::fopen("input.txt", "w+")) {
        std::fputs("123x", f);
        std::rewind(f);
        demo_scanf("%u%c", f);
        std::fclose(f);
    }
}

輸出

%u scanned 123
%c scanned 'x'

[編輯] 另請參閱

從檔案流中獲取一個字元
(function) [編輯]
C 文件 適用於 ungetc