2010-07-07 64 views
1

我有以下代碼(簡化):如何保留C++流的格式?

ostringstream oss; 

oss << "Text "; 

oss << hex << uppercase; 
oss.width(8); 
oss.fill('0'); 

oss << var1 << " "; 
oss << var2 << " "; 

oss << dec << nouppercase; 
oss.width(1); 

oss << var3 << " another text." << endl; 

string result = oss.str(); 
// work with result... 

var1var2unsigned int的和var3int。這個想法是創建一個字符串,其中var1var2按照十六進制數字(但沒有0x)和var3作爲常規整數形成。我發現些什麼,只有第一個數字正確格式化,第二個是不是用零填充:

Text 000AF00C 3B7FF 1 another text. 

一段時間,我發現,設置寬度和填充的參數重新修復之後。有沒有辦法避免爲每個數字反覆指定這些格式化規則?格式化變量的數量遠高於2,這只是一個簡單的例子。將所有這些包裝到一個函數中是一種選擇,但我真的很想了解如何使用ostringstream來保存格式。

+0

您確定它不僅僅是'width'被重置,因爲這將是您的實施中的錯誤? – 2010-07-07 11:02:13

+0

也許它只是寬度,沒有單獨測試寬度/填充。 – PeterK 2010-07-07 11:05:41

回答

4

對不起流格式的一些設置被稱爲揮發性(無關與關鍵字),你有每次設置它。 See here for explanation.

最好是創建自己的功能。

3

有沒有辦法如何避免爲每個數字反覆指定這些格式化規則?

不,there are manipulators which are sticky and there are those which are not。那些不必爲每個輸出重複的東西。

順便說一句,你可以塗抹一些語法糖,把

oss.width(8); 
oss.fill('0'); 

oss << var1 << " "; 

oss << std::setw(8) << std::setfill('0') << var1 << " "; 
+1

我覺得做一個粘性/不粘性的區別是誤導。所有的操縱器都有相同的效果:他們在流對象上設置了一些東西;只是執行一些格式化輸出操作的行爲需要調用(或調用)'.width(0)'作爲操作的顯式部分。 HTTP://計算器。com/questions/1532640/which-iomanip-manipulators-are-sticky/1533752#1533752 – 2010-07-07 11:07:27

+0

@Charles:看來我鏈接到的問題後來改爲反映這一點。 – sbi 2010-07-07 11:10:08

+0

你的意思是接受的答案?是的,在looong評論交流之後。 – 2010-07-07 11:29:11

1

像往常一樣,寫一個函數:

void WriteHex(unsigned int n, ostream & os ) { 
    os << hex << uppercase; 
    os.width(8); 
    os.fill('0'); 
    os << n; 
} 
0

您所有的格式設置應該除了width這是唯一保存下來,直到下一次格式化輸出過程中保留下來。這是因爲格式化輸出功能需要撥打width(0)作爲副作用。

一個合理簡潔的解決方案是在輸出操作需要非零寬度之前使用setw操縱器。

請注意,如果您設置了填充字符並且從最後一個數字輸出中保留了寬度8,則可能會對此輸出感到驚訝。

os << " ";