二進位制檔案比較小巧,但是不是人可讀的格式。文字檔案是一種人可讀的格式的檔案,為了操作這種檔案,我們需要使用QTextStream類。QTextStream和QDataStream的使用類似,只不過它是操作純文字檔案的。還有一些文字格式,比如XML、HTML,雖然可以由QTextStream生成,但Qt提供了更方便的XML操作類,這裡就不包括這部分內容了。
QTextStream會自動將 Unicode 編碼同作業系統的編碼進行轉換,這一操作對程式設計師是透明的。它也會將換行符進行轉換,同樣不需要你自己去處理。QTextStream使用16位的QChar作為基礎的資料儲存單位,同樣,它也支援C++標準型別,如int等。實際上,這是將這種標準型別與字串進行了相互轉換。
QTextStream同QDataStream使用基本一致,例如下面的程式碼將把“Thomas M. Disch: 334/n”寫入到 tmp.txt 檔案中:
- QFile file("sf-book.txt");
- if (!file.open(QIODevice::WriteOnly)) {
- std::cerr << "Cannot open file for writing: "
- << qPrintable(file.errorString()) << std::endl;
- return;
- }
- QTextStream out(&file);
- out << "Thomas M. Disch: " << 334 << endl;
可以看到,這段程式碼同前面的 QDataStream 相關程式碼基本雷同。文字檔案的寫入比較容易,但是讀出就不那麼簡單了。例如,
- out << "Denmark" << "Norway";
是我們寫入的程式碼。我們分別寫入兩個單詞,然後試圖以與二進位制檔案讀出的格式相同的形式讀出:
- in >> str1 >> str2;
上面兩段程式碼的 out 和 in 都是 QTextStream 型別的。雖然我們可以正常寫入,但讀出的時候,str1裡面將是 DenmarkNorway,str2 是空的。以文字形式寫入資料,是不能區分資料的截斷位置的。因為使用 QDataStream寫入的時候,實際上是要在字串前面寫如長度資訊的。因此,對於文字檔案,更多的是一種全域性性質的操作,比如使用 QTextStream::readLine() 讀取一行,使用 QTextStream::readAll() 讀取所有文字,之後再對獲得的QString物件進行處理。
預設情況下,QTextStream 使用作業系統的本地編碼進行讀寫。不過你可以使用 setCodec() 函式進行設定,比如
- stream.setCodec("UTF-8");
同 <iostream> 類似,QTextStream 也提供了一些用於格式化輸出的描述符,稱為stream manipulators。這些描述符放置在輸出內容之前,或者是使用相應的函式,用於對後面的輸出內容做格式化。具體的描述符如下
setIntegerBase(int) | |
0 | 讀出時自動檢測數字字首 |
2 | 二進位制 |
8 | 八進位制 |
10 | 十進位制 |
16 | 十六進位制 |
setNumberFlags(NumberFlags) | |
ShowBase | 顯示字首,二進位制顯示0b,八進位制顯示0,十六進位制顯示0x |
ForceSign | 在實數前面顯示符號 |
ForcePoint | 在數字中顯示點分隔符 |
UppercaseBase | 使用大寫的字首,如0B, 0X |
UppercaseDigits | 使用大寫字母做十六進位制數字 |
setRealNumberNotation(RealNumberNotation) | |
FixedNotation | 定點計數表示,如0.000123 |
ScientificNotation | 科學計數法表示,如1.23e-4 |
SmartNotation | 定點或科學計數法表示,自動選擇簡潔的一種表示法 |
setRealNumberPrecision(int) |
設定生成的最大的小數位數,預設是6 |
setFieldWidth(int) |
設定一個欄位的最小值,預設是0 |
setFieldAlignment(FieldAlignment) | |
AlignLeft | 左對齊 |
AlignRight | 右對齊 |
AlignCenter | 中間對齊 |
AlignAccountingStyle | 符號和數字之間對齊 |
setPadChar(QChar) |
設定對齊時填充的字元,預設是空格 |
比如,下面的程式碼
- out << showbase << uppercasedigits << hex << 12345678;
將輸出0xBC614E。或者我們可以這樣去寫:
- out.setNumberFlags(QTextStream::ShowBase | QTextStream::UppercaseDigits);
- out.setIntegerBase(16);
- out << 12345678;
QTextStream 不僅僅可以輸出到 QIODevice 上,也可以輸出到 QString 上面,例如
- QString str;
- QTextStream(&str) << oct << 31 << " " << dec << 25 << endl;