2012-02-06 12 views
17

Chcę serializować mój bufor protokołu na znak *. czy to możliwe? Wiem, że można serializować do pliku zgodnie z:C++ Bufory protokołów Google: serializować na char *?

fstream output("/home/eamorr/test.bin", ios::out | ios::trunc | ios::binary); 
if (!address_book.SerializeToOstream(&output)) { 
    cerr << "Failed to write address book." << endl; 
    return -1; 
} 

Ale chciałbym serializować do znaku w stylu C * dla transmisji w sieci.

Jak to zrobić? Pamiętaj, że jestem bardzo początkującym użytkownikiem C++.

Odpowiedz

34

To proste:

size_t size = address_book.ByteSizeLong(); 
void *buffer = malloc(size); 
address_book.SerializeToArray(buffer, size); 

Sprawdź documentation of MessageLite class również, że to klasa dominująca wiadomość i zawiera użytecznych metod.

+0

Jak uzyskać dostęp do funkcji SerializeToArray? Dzięki, – Eamorr

+1

int size = address_book.By teSize(); void * buffer = malloc (rozmiar); address_book.SerializeToArray (bufor, rozmiar); –

+0

Witaj Evgen, czy SerializeToArray został przestarzały czy coś? Używam najnowszej wersji buforów protokołu – Eamorr

9

Możesz serailze wyjście do ostringstream i użyć stream.str(), aby uzyskać ciąg, a następnie dostęp do ciągów znaków z string.c_str().

std::ostringstream stream; 
address_book.SerializeToOstream(&stream); 

string text = stream.str(); 
char* ctext = text.c_str(); 

Nie zapomnij podać sstream dla std::ostringstream.

+0

Legenda! Dziękuję bardzo za dostarczenie kodu. – Eamorr

+3

Jeszcze jedno - nie mam dostępnej funkcji SerializeToOstream - tylko SerializeWithCachedSizes (...) i SerializeWithCachedSizesToArray (...); ( – Eamorr

+3

Według dokumentów protobuf Google, format protobuf jest binarny, a zatem może zawierać zero Przebiegłem wiele razy, gdy wywołanie c_str() na wyjściu serializacji Protobufa skutkuje obciętym łańcuchem C, ponieważ bajty zerowe są zapisywane do podanego bufora, a dalsze użycie tego bufora z normalnymi funkcjami w stylu C interpretuje je jako kończące się z terminatorem zerowym Nie polecam w ogóle korzystania z tej metody - szczerze mówiąc, nie sądzę, że kiedykolwiek będzie bezpieczne serializowanie protobufów do ciągów w stylu C, i to prawdopodobnie dlatego Google nie zapewnia tej opcji –

3

Można użyć ByteSize aby uzyskać liczbę bajtów komunikat zajmie a następnie SerializeToArray aby wypełnić tablicę z zakodowaną wiadomością.

0

Jeszcze jedna linia kodu, aby zadbać o to, aby zserializowane dane mogły zawierać zero.

std::ostringstream stream; 
address_book.SerializeToOstream(&stream); 

string text = stream.str(); 
char* ctext = text.c_str(); // ptr to serialized data buffer 
// strlen(ctext) would wrongly stop at the 1st 0 it encounters. 
int data_len = text.size(); // length of serialized data