Я делал это бесчисленное количество раз раньше: это очень распространенный сценарий. Есть ряд вещей, которые я практически всегда делаю.
Не беспокойтесь о том, чтобы сделать его наиболее эффективным из доступных.
Если мы тратим много времени на упаковку и распаковку пакетов, то мы всегда можем изменить это, чтобы сделать его более эффективным. Хотя я еще не сталкивался со случаем, когда мне пришлось это делать, я не реализовывал сетевые маршрутизаторы!
Хотя использование структур / объединений является наиболее эффективным подходом с точки зрения времени выполнения, оно сопряжено с рядом сложностей: убедить компилятор упаковать структуры / объединения, чтобы они соответствовали структуре октетов нужных вам пакетов, стараясь избежать выравнивания проблемы с порядком байтов и отсутствием безопасности, так как нет возможности или почти нет возможности проверять работоспособность отладочных сборок.
Я часто сталкиваюсь с архитектурой, включающей в себя следующие вещи:
- Базовый класс пакета. Любые общие поля данных доступны (но не могут быть изменены). Если данные не хранятся в упакованном формате, то есть виртуальная функция, которая создаст упакованный пакет.
- Количество классов представления для определенных типов пакетов, полученных из общего типа пакета. Если мы используем функцию упаковки, то каждый класс представления должен реализовать ее.
- Все, что может быть выведено из определенного типа класса представления (то есть идентификатора типа пакета из общего поля данных), рассматривается как часть инициализации и не может быть изменено в противном случае.
- Каждый класс представления может быть создан из неупакованного пакета или будет терпеть неудачу, если данные пакета недопустимы для этого типа. Это может быть упаковано на фабрике для удобства.
- Если у нас нет доступных RTTI, мы можем получить «RTTI для бедняков», используя идентификатор пакета, чтобы определить, к какому конкретному классу представления относится объект.
Во всем этом можно (даже если только для отладочных сборок) проверить, что для каждого изменяемого поля установлено правильное значение. Хотя это может показаться большой работой, очень сложно получить неверно отформатированный пакет, содержимое предварительно упакованных пакетов может быть легко проверено на глаз с помощью отладчика (поскольку все это в обычных переменных формата, встроенных в платформу).
Если нам нужно реализовать более эффективную схему хранения, это тоже может быть включено в эту абстракцию с небольшими дополнительными затратами на производительность.