Quali sono le buone soluzioni per la serializzazione in C ++? [chiuso]


18

Sono curioso di sapere quali soluzioni hanno sviluppato gli sviluppatori di giochi per serializzare i diversi tipi di dati che gestiscono per i loro giochi. Ragazzi, utilizzate qualche gerarchia monolitica di GameObject che ospita un'interfaccia di serializzazione per tipi derivati, utilizzate una sorta di soluzione personalizzata basata su RTTI, eseguite serializzazione esplicita del flusso per determinate classi o utilizzate alcune delle soluzioni open source (boost :: serialization, s11n, eccetera).


1
Penso che la serializzazione nella programmazione dello sviluppo di giochi sia un argomento importante, ma questa domanda non mi piace. Che cosa stai cercando di fare? Quali problemi specifici stai cercando di risolvere? Invece, l'ho convertito in un wiki della comunità in modo che sia più un formato di discussione.
Tetrad,

Penso che sarebbe utile applicare alcune formulazioni a questo, (come per la domanda sul controllo della versione).
Jesse Dorsey

Risposte:


9

I buffer di protocollo di Google possono essere un approccio piuttosto valido per la serializzazione di oggetti c ++. Potrebbe essere necessario creare alcuni oggetti intermedi come parte del processo di serializzazione, ma funziona anche su molte piattaforme e lingue.


1
Lo sto usando ed è facile se puoi automatizzare la generazione del codice nel tuo sistema di compilazione. Anche se un vantaggio davvero eccellente è che ti consente di trasferire dati su macchine remote senza riguardo alla piattaforma utilizzata, ed è ottimizzato per questo, quindi gli oggetti generati non sono grandi.
Klaim

10

Nel nostro gioco utilizziamo semplicemente boost.serilization , è facile da usare e molto veloce, ma secondo me è utile solo per i salvataggi. Se provi a creare personaggi, ti consiglio qualcosa di basato su XML'ish o JSON, perché sono facili da leggere e modificabili anche se non hai l'editor.


Ho visto boost :: serializzazione utilizzata con successo anche per la comunicazione client / server. Tuttavia, AFAIK è basato su stream, quindi non è esattamente tollerante alla versione. Potrebbe non essere un problema per la comunicazione client / server, ma se lo si utilizza per i giochi salvati, qualsiasi modifica alle strutture dei dati di gioco rende impossibile il caricamento di giochi salvati più vecchi (il supporto per il caricamento di versioni di oggetti più vecchi diventa un vero lavoro di routine) ).
Mike Strobel,

2
@MikeStrobel Di recente stavo recensendo alcuni kit di serializzazione e json e mi sono imbattuto in questo commento. boost :: serialization supporta esplicitamente il versioning. Le chiamate serializzate possono ricevere un numero di versione e quindi spetta all'utente implementare la logica di ramificazione di base (se (versione> 1.0) ...). Nel complesso sembra piuttosto robusto.
M2tM,

Peccato che non supporti l'allocatore / deleter personalizzato.
JamesAMD,

1
Sono appena passato dal potenziamento della serializzazione ai cereali. Il porto era straordinariamente fluido . Ha funzionato come un fascino. Il cereale supporta xml, json, binario e binario portatile . Il motivo per cui ho portato i cereali era l'ultimo. Avevo bisogno di archivi binari portatili perché eseguo un server a cui si collegano i client (per ora un mac, presto iOS e Android). Sono stato abbastanza contento di aumentare la serializzazione, ma penso che alcune delle caratteristiche del cereale facciano un passo avanti in un modo migliore, come la menzionata serializzazione binaria portatile. Per i buffer del protocollo di interoperabilità linguistica e tale è meglio.
Germán Diago,

Per documenti boost.serialization non è thread-safe. Né è Cereal che utilizza un'API simile.
Hi-Angel,


2

Google FlatBuffers è un'efficace libreria di serializzazione multipiattaforma per C ++, con supporto per Java e Go. È stato creato su Google appositamente per lo sviluppo di giochi e altre applicazioni critiche per le prestazioni.

È disponibile come open source sotto la licenza Apache, v2.



1

XDS è stato progettato proprio per questo scopo, offre i vantaggi di XML durante lo sviluppo e i vantaggi di una rappresentazione binaria compatta al momento della distribuzione.


Non sono davvero sicuro di cosa differenzi l'XDS dai buffer del protocollo di Google? Sembrano servire allo stesso scopo, tranne per il fatto che XDS è stato il primo.
jacmoe,

Intendi sicuramente XSD e non XDS? codesynthesis.com/products/xsd Volevo inviare una risposta al riguardo per completare l'elenco.
v.oddou,

1

Se si utilizza una piattaforma Linux, è possibile utilizzare direttamente la json.hlibreria per la serializzazione. Ecco un esempio di codice che ho trovato. Fonte: Json Serializer

//============================================================================
// Name        : JsonTest.cpp
// Author      : Manis Kumar Khedawat
//============================================================================

#include <iostream>
#include <json/json.h>

using namespace std;

struct objStruct{
    string str;
    int n1;
    int n2;
};

typedef objStruct obj;

void serializeToJson(json_object *jObj,obj* pObj)
{
    /*
    string str;
    int n1;
    int n2;
    */

    // Create json object for every member in struct Obj.

    json_object *jstr = json_object_new_string (pObj->str.c_str());
    json_object *jn1 =json_object_new_int(pObj->n1);
    json_object *jn2 =json_object_new_int(pObj->n2);

    // Add all above created object into jObj

    json_object_object_add(jObj,"str",jstr);
    json_object_object_add(jObj,"n1",jn1);
    json_object_object_add(jObj,"n2",jn2);

    // pObj is Serialzed into jObj
}

void deSerializeToJson(json_object *jObj,obj* pObj)
{
    /*
    string str;
    int n1;
    int n2;
    */

    // Get every member as different json obj from jObj
    json_object *jstr = json_object_object_get (jObj,"str");
    json_object *jn1 =json_object_object_get(jObj,"n1");
    json_object *jn2 =json_object_object_get(jObj,"n2");

    pObj->str=json_object_get_string(jstr);
    pObj->n1=json_object_get_int(jn1);
    pObj->n2=json_object_get_int(jn2);

    // jObj is DeSerialzed into pObj
}

int main() {
    // Lets Create an Object which we will serialze into Json
    obj obj1;
    obj1.n1=3;
    obj1.n2=6;
    obj1.str="This is String";

    // Create a json Object
    json_object* jObj=json_object_new_object();

    // To serialize into Json Object
    // Please Keep in mind , we are passing address of object (pointer) & not object
    serializeToJson(jObj,&obj1);

    obj obj2;
    // To serialize into Json Object
    // Please Keep in mind , we are passing address of object (pointer) & not object
    deSerializeToJson(jObj,&obj2);

    cout<<"String str == "<<obj2.str<<endl;
    cout<<"n1 & n2 : "<<obj2.n1<<" "<<obj2.n2<<endl;

    return 0;
}

0

Entrambi i buffer jsonCpp e Protocol sono buone opzioni. Per quanto ne so, entrambi ti permetteranno solo di creare strutture ad albero seriale fuori dalla scatola (per favore correggimi se sbaglio). boost :: la serializzazione può gestire grafici arbitrari, ma non ha un bel formato di testo come json (penso che ci sia un formato xml)

Personalmente penso che l'approccio per la serializzazione json adottato da Dojo sia il migliore
http://docs.dojocampus.org/dojox/json/ref

Ne ho creato la mia versione in c ++ usando jsoncpp, che deserializzerà anche gli oggetti digitati (ho una specie di grande fabbrica per tutti i miei tipi). Mi permette di creare una scena da una raccolta di file json a cui è possibile fare riferimento comunque, per favore.

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.