Câu trả lời:
Tôi đã sử dụng một chuỗi rõ ràng và str trong quá khứ:
// clear, because eof or other bits may be still set.
s.clear();
s.str("");
Điều này đã làm điều này cho cả hai chuỗi đầu vào và đầu ra. Ngoài ra, bạn có thể xóa thủ công, sau đó tìm kiếm trình tự phù hợp để bắt đầu:
s.clear();
s.seekp(0); // for outputs: seek put ptr to start
s.seekg(0); // for inputs: seek get ptr to start
Điều đó sẽ ngăn chặn một số phân bổ lại được thực hiện bằng str
cách ghi đè bất cứ thứ gì trong bộ đệm đầu ra hiện tại thay thế. Kết quả là như thế này:
std::ostringstream s;
s << "hello";
s.seekp(0);
s << "b";
assert(s.str() == "bello");
Nếu bạn muốn sử dụng chuỗi cho các hàm c, bạn có thể sử dụng std::ends
, đặt null kết thúc như thế này:
std::ostringstream s;
s << "hello";
s.seekp(0);
s << "b" << std::ends;
assert(s.str().size() == 5 && std::strlen(s.str().data()) == 1);
std::ends
là một bản tường thuật của phần không dùng nữa std::strstream
, có thể ghi trực tiếp vào một mảng char mà bạn đã phân bổ trên ngăn xếp. Bạn phải chèn null kết thúc bằng tay. Tuy nhiên, std::ends
tôi không phản đối, tôi nghĩ bởi vì nó vẫn hữu ích như trong các trường hợp trên.
s.str("");
thay thế. auto str = s.str(); auto cstr = str.c_str(); file << cstr; s.clear(); s.seekp(0); s << ends;
boost::any a = 1; std::ostringstream buffer; buffer << a << std::ends; EXPECT_EQ( buffer.str(), "any<(int)1>" );
TestUtilsTest.cpp:27: Failure Expected: buffer.str() Which is: "any<(int)1>\0" To be equal to: "any<(int)1>"
và nếu tôi sử dụng lại với các chuỗi có độ dài khác nhau, tôi sẽ nhận được các bit còn lại
s.seekp(0); s << std::ends; s.seekp(0);
Có vẻ là ostr.str("")
cuộc gọi thực hiện các mẹo.
Nếu bạn định xóa bộ đệm theo cách sẽ khiến nó bị xóa trước khi sử dụng lần đầu tiên, bạn sẽ cần thêm một cái gì đó vào bộ đệm trước w / MSVC.
struct Foo {
std::ostringstream d_str;
Foo() {
d_str << std::ends; // Add this
}
void StrFunc(const char *);
template<class T>
inline void StrIt(const T &value) {
d_str.clear();
d_str.seekp(0); // Or else you'll get an error with this seek
d_str << value << std::ends;
StrFunc(d_str.str().c_str()); // And your string will be empty
}
};
clear
sẽ gây ra sự failbit
trở thành bộ nếu dòng trống. Trong khi chỉ cần gọi seekp
nên trở lại nếu không có luồng.
Bạn không. Sử dụng hai luồng được đặt tên khác nhau cho rõ ràng và để trình biên dịch tối ưu hóa tìm ra rằng nó có thể sử dụng lại luồng cũ.
ostringstream
(dựa trên dữ liệu đã đọc) và sau đó phải viết chuỗi được xây dựng ở ostringstream
đâu đó theo thời gian (ví dụ sau khi đọc một chuỗi ký tự nhất định) và bắt đầu xây dựng một chuỗi mới.