2010-06-10 43 views
20

Xác nhận của tài liệu tuần tự hóa tăng khẳng định rằng cách sắp xếp/deserialize các mục đang sử dụng lưu trữ nhị phân/văn bản với luồng trên cấu trúc bên dưới. Điều này làm việc tốt nếu tôi wan't sử dụng dữ liệu serialized như là một std :: string, nhưng ý định của tôi là chuyển đổi nó trực tiếp vào một bộ đệm char *. Làm thế nào tôi có thể đạt được điều này mà không cần tạo một chuỗi tạm thời?Nối tiếp tăng tiếp trực tiếp vào mảng char

Giải quyết! Đối với những người muốn có ví dụ:

char buffer[4096]; 

boost::iostreams::basic_array_sink<char> sr(buffer, buffer_size); 
boost::iostreams::stream< boost::iostreams::basic_array_sink<char> > source(sr); 

boost::archive::binary_oarchive oa(source); 

oa << serializable_object; 
+0

Mặt khác, tại sao bạn sẽ từ bỏ việc quản lý bộ nhớ miễn phí và rò rỉ rủi ro và tràn ngập :)? –

+0

Đáng buồn thay, vì các vấn đề về hiệu suất: ( – scooterman

Trả lời

6

IIUC, bạn muốn viết cho một mảng có kích thước cố định.

Bạn có thể sử dụng boost::iostreams::array_sink (được gói với stream để cung cấp cho nó giao diện std :: ostream) cho điều đó.

+0

@op: Cảm ơn, điều đó đã hoạt động như một sự quyến rũ! Tôi chỉ muốn tăng cường đó có thêm tài liệu: ( – scooterman

31

Nếu bạn không biết kích thước của dữ liệu bạn đang gửi trước, đây là một cách tổng quát để serialize vào một std::string:

// serialize obj into an std::string 
std::string serial_str; 
boost::iostreams::back_insert_device<std::string> inserter(serial_str); 
boost::iostreams::stream<boost::iostreams::back_insert_device<std::string> > s(inserter); 
boost::archive::binary_oarchive oa(s); 

oa << obj; 

// don't forget to flush the stream to finish writing into the buffer 
s.flush(); 

// now you get to const char* with serial_str.data() or serial_str.c_str() 

Để deserialize, sử dụng

// wrap buffer inside a stream and deserialize serial_str into obj 
boost::iostreams::basic_array_source<char> device(serial_str.data(), serial_str.size()); 
boost::iostreams::stream<boost::iostreams::basic_array_source<char> > s(device); 
boost::archive::binary_iarchive ia(s); 
ia >> obj; 

này hoạt động như một sự quyến rũ, tôi sử dụng nó để gửi dữ liệu xung quanh với MPI.

Điều này có thể được thực hiện rất nhanh nếu bạn giữ serial_str trong bộ nhớ và chỉ cần gọi serial_str.clear() trước khi bạn đăng nhập vào nó. Điều này xóa dữ liệu nhưng không giải phóng bất kỳ bộ nhớ nào, vì vậy sẽ không có sự phân bổ nào xảy ra khi kích thước dữ liệu tuần tự hóa tiếp theo của bạn không yêu cầu nó.

+0

Câu trả lời tuyệt vời! Tôi đang cố gắng giữ bộ đệm trong bộ nhớ như bạn đề xuất, nhưng nó có vẻ gọi serial_str.clear() là không đủ - tôi cũng cần phải thiết lập lại để binary_orachive hoặc back_inserter_device bằng cách nào đó, để nói với nó để quay trở lại văn bản trong đầu serial_str? –

+0

@omer, trong mã của tôi, tôi đã chỉ 'std :: string serial_str' như là một biến thành viên, và tái tạo mọi thứ khác mỗi khi tôi gửi một cái gì đó. – martinus

+0

Giải pháp này là những gì tôi đã tìm kiếm. Cảm ơn! – aardvarkk

Các vấn đề liên quan