Beste tweakerts en andersoortigen,
Ik ben op dit moment bezig met het schrijven van een refactoringsvoorstel voor een demo spel bij een bepaalde 3D engine (voor punten op school hoofdzakelijk), en ik zit met het volgende 'probleem'.
Binnen de engine wordt gebruik gemaakt van een berichtsysteem waarbij berichten tussen de server en clients gestuurd kunnen worden. Een bericht is altijd een subclass van Message, en bevat de gegevens die verstuurd moeten worden als class variables. Een bericht bevat altijd twee methoden, een Compress en een Decompress methode die de class variables in een Compressor resp. uit een Decompressor haalt:
Dat is verder strak enzo. Het probleem (als je het echt een probleem wilt noemen, mijns insziens is het gewoon iets wat handiger / flexibeler kan) is hierbij dat voor elk type bericht je een nieuwe class moet schrijven. Dit heeft als resultaat dat je drie verschillende Message types hebt die, bijvoorbeeld, allemaal een long waarde versturen over het netwerk. Dit zou je op kunnen lossen door gewoon een LongMessage klasse te definieren en daar een bericht identifier aan mee te geven, echter dit is maar een gedeeltelijke oplossing.
Een betere, flexibelere en uiteindelijk minder 'arbeidsintensieve' manier is om een design pattern te gebruiken, de meest logische hierbij is het Composite design pattern, waar je, om het zo te beschrijven, een complex object samen kunt stellen uit eenvoudigere objecten.
In dit geval zat ik te denken aan een structuur waarbij er een berichttype (of berictttypeonderdeel) voor elke basiswaarde gedefinieerd wordt (een voor long, voor float etc), die gebruikt kunnen worden om complexere objecten samen te stellen die, bijvoorbeeld, posities in 3D ruimte doorgeven (die eigenlijk gewoon 3 long of float waarden zijn). Uiteindelijk komt er een verzameling functies die berichttypen samenstelt uit deze basisonderdelen (factory method / builder patroon).
Echter, ik loop vast op het weer ophalen van de gegevens uit een composiet bericht. Een composiet bericht bevat in dit geval een X aantal andere composiete berichten, die van het type LongMessage, BoolMessage of, complexer, Vector3DMessage kunnen zijn.
Mijn vraag is dus nu als volgt: Hoe kan ik netjes vaststellen welk type een bepaald berichtcomponent is, en zijn gegevens eruithalen? Met netjes bedoel ik dat ik liever niet een structuur wil hebben waarbij elk component zijn eigen identifier heeft (een numerieke waarde oid) die door een switch gehaald kan worden en zodanig gecast kan worden naar zijn specifieke type.
Zijn daar ook ideeen over? Andere oplossingen? Het basisidee is om een complex berichttype samen te stellen uit eenvoudigere componenten, maar de informatie moet ook weer uit deze componenten gehaald kunnen worden, zodanig dat een ontvanger ook iets aan deze informatie heeft.
De standaarddefinitie van een Composite design pattern houdt daar namelijk geen rekening mee, en definieert alleen dat een onderdeel van een compositie een bepaalde operatie heeft die uitgevoerd kan worden.
Ik ben op dit moment bezig met het schrijven van een refactoringsvoorstel voor een demo spel bij een bepaalde 3D engine (voor punten op school hoofdzakelijk), en ik zit met het volgende 'probleem'.
Binnen de engine wordt gebruik gemaakt van een berichtsysteem waarbij berichten tussen de server en clients gestuurd kunnen worden. Een bericht is altijd een subclass van Message, en bevat de gegevens die verstuurd moeten worden als class variables. Een bericht bevat altijd twee methoden, een Compress en een Decompress methode die de class variables in een Compressor resp. uit een Decompressor haalt:
C++:
1
2
3
4
5
6
7
8
9
10
11
12
| // pleurt gegevens in de compressor void SomeMessageType::Compress(Compressor& data) const { data << someClassVariable; } // haalt gegevens uit de decompressor in de class var. bool SomeMessageType::Decompress(Decompressor& data) { data >> someClassVariable; return true; } |
Dat is verder strak enzo. Het probleem (als je het echt een probleem wilt noemen, mijns insziens is het gewoon iets wat handiger / flexibeler kan) is hierbij dat voor elk type bericht je een nieuwe class moet schrijven. Dit heeft als resultaat dat je drie verschillende Message types hebt die, bijvoorbeeld, allemaal een long waarde versturen over het netwerk. Dit zou je op kunnen lossen door gewoon een LongMessage klasse te definieren en daar een bericht identifier aan mee te geven, echter dit is maar een gedeeltelijke oplossing.
Een betere, flexibelere en uiteindelijk minder 'arbeidsintensieve' manier is om een design pattern te gebruiken, de meest logische hierbij is het Composite design pattern, waar je, om het zo te beschrijven, een complex object samen kunt stellen uit eenvoudigere objecten.
In dit geval zat ik te denken aan een structuur waarbij er een berichttype (of berictttypeonderdeel) voor elke basiswaarde gedefinieerd wordt (een voor long, voor float etc), die gebruikt kunnen worden om complexere objecten samen te stellen die, bijvoorbeeld, posities in 3D ruimte doorgeven (die eigenlijk gewoon 3 long of float waarden zijn). Uiteindelijk komt er een verzameling functies die berichttypen samenstelt uit deze basisonderdelen (factory method / builder patroon).
Echter, ik loop vast op het weer ophalen van de gegevens uit een composiet bericht. Een composiet bericht bevat in dit geval een X aantal andere composiete berichten, die van het type LongMessage, BoolMessage of, complexer, Vector3DMessage kunnen zijn.
Mijn vraag is dus nu als volgt: Hoe kan ik netjes vaststellen welk type een bepaald berichtcomponent is, en zijn gegevens eruithalen? Met netjes bedoel ik dat ik liever niet een structuur wil hebben waarbij elk component zijn eigen identifier heeft (een numerieke waarde oid) die door een switch gehaald kan worden en zodanig gecast kan worden naar zijn specifieke type.
Zijn daar ook ideeen over? Andere oplossingen? Het basisidee is om een complex berichttype samen te stellen uit eenvoudigere componenten, maar de informatie moet ook weer uit deze componenten gehaald kunnen worden, zodanig dat een ontvanger ook iets aan deze informatie heeft.
De standaarddefinitie van een Composite design pattern houdt daar namelijk geen rekening mee, en definieert alleen dat een onderdeel van een compositie een bepaalde operatie heeft die uitgevoerd kan worden.