2011-09-19 17 views
1

我有一個函數(遺留)讀取文件的前幾行來確定它的類型,然後關閉並重新打開該文件,以便它可以使用正確的解釋器重新讀取整個文件。要點是:什麼樣的輸入流可以調用seekg?

void readFile(const char *filename) { 
    ifstream is(filename); 
    Filetype ft = determineFileType(is); 
    is.close(); 
    is.open(filename); 
    parseFile(is, ft); 
} 

我需要一個類似的功能,可以在已經打開的流上工作。我創建了一個新的函數,它的ostream &而不是char *filename - 基本上是這樣的:

void readFile(istream &is) { 
    std::ios::streampos pos = is.tellg(); 
    Filetype ft = determineFileType(is); 
    is.seekg(pos); 
    parseFile(is, ft); 
} 

看來工作時istream實際上是stringstreamfstream,但我不知道如果我剛開始很幸運。我也在seekg -ing std::cin上做了一個小測試,結果很奏效,這讓我很吃驚。

所以我的問題:你允許使用什麼樣的流seekg?什麼時候會失敗?規範參考將是很好的 - 我看透了,seekg,pubseekpos,seekpos,seekoff的東西根本沒有幫助。

我想重新實現原來的新功能(如下),但我不知道這是否安全。

void readFile(const char *filename) { 
    ifstream is(filename); 
    readFile(is); 
    is.close(); 
} 
+0

我認爲'seekg'是爲所有輸入流實現的,但如果流不可搜索,它可能只是一個無操作。 –

+0

對,它是爲所有'istream's實現的,但它可能會失敗並設置'failbit'我認爲。只是想知道是否有什麼規格可能會發生什麼 - 就像'fstream'一樣,它可以保證正常工作,而'std :: cin'則依賴於實現。 – Dan

回答

1

可以給出的唯一真正的答案是它在它的工作原理中起作用。在 的案例std::stringbuf,它應該到處工作。在 std::filebuf的情況下,是否有效取決於系統;如果filebuf在實際文件上打開,但 通常會失敗(如果系統沒有報告錯誤,則可能是靜靜地) 對於許多其他類型的輸入:從鍵盤或命名管道,通常會工作 ,例如 。

更健壯的解決方案是緩存初始輸入,並從緩存中重新讀取。

+0

我很害怕這個。太糟糕了,沒辦法告訴我有什麼_sind_我有'istream'。我同意緩存是一個更好的解決方案。儘管如此,我正努力減少破壞現有代碼的機會。感謝你的回答! – Dan

相關問題