[英]Using ifstream when filename contains wide characters
在Windows 7中使用C ++ Builder XE5(bcc32)。
我正在嘗試打開一個文件名包含寬字符的文件。 我正在測試的實際文件名是C:\\bΛx\\foo.txt
。 那里的非ASCII字符是U + 039B。
我已將此文件名正確存儲在std::wstring
。 但是,嘗試:
std::ifstream f( filename.c_str() );
無法打開文件。
當然,在標准C ++中, fopen
僅使用char *
。 但是,Dinkumware C ++ RTL實現具有接受wchar_t *
的重載。 不幸的是,在...\\Embarcadero\\RAD Studio\\12.0\\source\\cpprtl\\Source\\dinkumware\\source\\fiopen.cpp
中實現該重載不會調用_wfopen
。 而是使用wcstombs
將字符串轉換為UTF-8,然后調用fopen
。
檢查源代碼是否存在fopen
,它會調用基礎函數___topen
的窄版,該函數最終將UTF-8字符串傳遞給CreateFile
。
當我檢查使用Sysinternals Process Monitor打開文件的嘗試時,它表明它確實嘗試使用UTF-8文件字符串打開文件,並且操作系統拒絕了該結果,結果為NAME COLLISION
。
如果我使用_wfopen( filename.c_str(), L"r" )
打開文件_wfopen( filename.c_str(), L"r" )
那么一切都很好,我可以使用CI / O函數讀取文件,但是我當然不能使用C ++ iostream。
有什么方法可以使用std::ifstream
打開帶有U + 039B或文件名中其他類似字符的文件?
請注意,使用std::wifstream
也不起作用(它仍然嘗試打開文件名的UTF-8版本)。
如果我使用
_wfopen( filename.c_str(), L"r" )
打開文件_wfopen( filename.c_str(), L"r" )
那么一切都很好,我可以使用CI / O函數讀取文件,但是我當然不能使用C ++ iostream。
我看不到“當然”。 您的問題已減少到從FILE*
制作iostreams streambuf
。 Howard Hinnant 在此處回答說,標准沒有提供任何方法,但是在FILE*
之上實現streambuf
派生的類非常簡單。 他甚至提到一些他認為是一個很好的起點的代碼。
請注意,這僅對文本文件有意義。 iostream和二進制文件不相處; 有一個字符編碼層, ios_base::binary
不會將其關閉。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.