Pergunta

Em geral, qual é a melhor maneira de armazenar dados binários em C ++? As opções, tanto quanto eu posso dizer, praticamente se resumem ao uso de cordas ou vector s. (Eu vou omitir a possibilidade de char * s e malloc () é desde que eu estou me referindo especificamente para C ++).

Normalmente, eu uso apenas uma corda, no entanto eu não tenho certeza se existem despesas gerais estou em falta, ou conversões que STL faz internamente essa confusão poderia com a sanidade de dados binários. Alguém tem qualquer ponteiros (RAH) sobre este assunto? Sugestões ou preferências de uma maneira ou de outra?

Foi útil?

Solução

vetor de char é bom porque a memória é contiguious. Portanto, você pode usá-lo com um monte de C API, tais como soquetes Berkley ou APIs de arquivo. Você pode fazer o seguinte, por exemplo:

  std::vector<char> vect;
  ...
  send(sock, &vect[0], vect.size());

e ele vai funcionar bem.

Você pode essencialmente tratá-lo como qualquer outro char buffer alocada dinamicamente. Você pode digitalizar cima e para baixo à procura de números mágicos ou padrões. Você pode analisá-lo parcialmente no lugar. Para receber a partir de uma tomada você pode muito facilmente redimensioná-la para acrescentar mais dados.

A desvantagem é o redimensionamento não é muito eficiente (redimensionamento ou preallocate prudentemente) e exclusão de frente da matriz também será muito terminais ineficientes. Se você precisar, digamos, pop apenas um ou dois caracteres de cada vez fora da parte dianteira da estrutura de dados com muita freqüência, copiar para um deque antes desta transformação pode ser uma opção. Isso você custos de cópia e de memória deque não é contíguo, para que você não pode simplesmente passar um ponteiro para uma API C.

A linha inferior, aprender sobre as estruturas de dados e suas vantagens e desvantagens antes de mergulhar, no entanto vetor de char é tipicamente o que eu vejo utilizado na prática geral.

Outras dicas

O maior problema com std :: string é que o padrão atual não garante que o seu armazenamento subjacente é contíguo. No entanto, não há implementações STL conhecidos onde cadeia não é contígua, assim, na prática, provavelmente não irá falhar. Na verdade, o novo C ++ 0x padrão vai corrigir esse problema, determinando que std :: string usa um buffer contíguo, como std :: vector.

Outro argumento contra cordas é que o próprio nome sugere que ele contém uma cadeia de caracteres, não um buffer binário, o que pode causar confusão para aqueles que ler o código.

Dito isso, eu recomendo vector também.

Eu uso std::string para isso também, e nunca tive um problema com ele.

Um "ponteiro", que acabei de receber um lembrete afiada de um pedaço de código ontem: ao criar uma string de um bloco de dados binários, use o formulário construtor std::string(startIter, endIter), não a forma std::string(ptr, offset, length) - este último faz com que o suposição de que o ponteiro aponta para uma cadeia de estilo C, e ignora qualquer coisa após o primeiro caractere zero (ele copia "até" o length especificado, não caracteres length).

Você certamente deve estar usando algum recipiente de char, mas o recipiente que você deseja utilizar depende da sua aplicação.

Chars têm várias propriedades que os tornam úteis para a exploração dos dados binários: os proíbe padrão qualquer "preenchimento" para um tipo de dados char, o que é importante, uma vez que significa que você não terá de lixo em seu layout binário. Cada caractere também está garantido para ser exatamente um byte, tornando-o único e velho tipo de dados (POD) com largura definida (todos os outros são especificadas em termos de limites superiores e / ou inferiores).

A discussão sobre contêiner stl apropriada com a qual para armazenar os caracteres é tratado pelo bem por Doug acima. Qual deles você precisa depende inteiramente do seu caso de uso. Se você está apenas segurando um bloco de dados que você iterate através de, sem qualquer pesquisa, acrescentar / remover ou necessidades especiais de emenda, eu preferiria vector, o que torna as suas intenções mais clara do que std :: string, que muitas bibliotecas e funções assumirá detém uma seqüência c-style terminada em null.

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top