Общее чтение правильно сформированного двоичного файла - PullRequest
3 голосов
/ 14 сентября 2009

Я пытаюсь прочитать содержимое файлов карты / модели игры в программу с целью написания небольшого средства просмотра моделей и тестирования некоторых функций DirectX. Форматы файлов модели / карты носят фрагментарный характер, и я знаю формат этих файлов. Я могу легко читать файлы, анализируя отдельные фрагменты, используя такой подход:

class FileType1 {
    private Chunk1 c1;
    private Chunk2 c2; // etc

    public void Read(BinaryReader reader) {
        c1 = new Chunk1(reader);
        c2 = new Chunk2(reader);
    }
}

Однако я пытаюсь придумать какой-то способ общего чтения этих файлов, указав формат, которому придерживается файл (т. Е. За Chunk1 следует Chunk2 и т. Д.), Чтобы читатель мог убедиться, что файл имеет соответствующую структуру , Я могу использовать суперкласс Chunk и фабрику Chunk для общего чтения всех фрагментов в любом файле. По сути, я хотел бы дополнить это дополнительными функциональными возможностями валидатора структуры (или чего-то подобного), чтобы получить метод, подобный следующему:

public void Read(BinaryReader reader, ChunkFileFormat format) {
    while (!EOF) {
        char[] chunkID = reader.ReadChars(4);
        Chunk c = chunkFactory.Create(chunkID);
        if (c.GetType() != format.Next.GetType())
            throw new Exception("File format is invalid");
        format.SetCurrentRecord(c);
    }
}

Идея заключается в том, что класс ChunkFileFormat определяет структуру файла, указывая, какой тип чанка ожидается при следующем чтении из двоичного потока. Это позволило бы подклассам ChunkFileFormat указывать макет этого конкретного формата, и один метод чтения мог бы использоваться для чтения всех различных форматов фрагментированных файлов, вместо того, чтобы писать длинный и повторяющийся метод для каждого.

Мой вопрос: кто-нибудь знает шаблоны проектирования или подходы, которые могут справиться с этой ситуацией? Проект, над которым я работаю, в настоящее время написан на C #, хотя меня могут заинтересовать решения на C ++ (или на любом другом языке).

Заранее спасибо!

Ответы [ 2 ]

2 голосов
/ 15 сентября 2009

Правила такого типа легко кодируются с помощью конечного автомата .

Каждый чанк должен менять состояние, в котором вы находитесь. Каждое состояние, ожидающее определенных чанков впоследствии. Если вы столкнулись с порцией, с которой вы не должны сталкиваться в течении, это ошибка.

0 голосов
/ 14 сентября 2009

Вы можете создать формальное описание формата, используя DataScript / antlr и заставить его создавать для вас синтаксический анализ и код ввода / вывода (Java или C ++).

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...