Devo usar a sequência de bits do PostgreSQL?

18

bit stringUltimamente tenho aprendido sobre o tipo de dados e estou bastante curioso sobre:

  1. Na parte inferior desta página de documento, há a frase:

    ... mais sobrecarga de 5 ou 8 bytes, dependendo do comprimento da string

  2. Como as seqüências de bits são tratadas em outras linguagens como PHP, Java, C #, C ++ etc., por meio de drivers como Npgsql, ODBC etc.

Para a pergunta 1, o uso de smallint ou bigint será muito mais eficiente em armazenamento e talvez ofereça um ganho de desempenho, já que os números inteiros são suportados em todos os lugares. A maioria das linguagens de programação manipula operações de bits em números inteiros com facilidade. Se for esse o caso, qual é o sentido de introduzir o tipo de dados de cadeia de bits? É apenas para casos que precisam de uma grande quantidade de máscaras de bits? Indexação de campo de bits, talvez? Estou mais curioso sobre como a indexação de campo de bits é feita no PostgreSQL.

No segundo, estou confuso, mais do que curioso. Por exemplo, e se eu armazenar máscaras de bit do dia da semana em um campo de bit (7), um bit por dia, com o bit mais baixo representando segunda-feira. Então eu procuro o valor em PHP e C ++. O que vou receber? A documentação diz que terei uma sequência de bits, no entanto, uma sequência de bits não é algo que eu possa usar diretamente - como acontece com números inteiros. Então, neste caso, devo desistir do campo de bits?

Alguém pode explicar por que e quando devo usar variações de bits?

Jackey Cheung
fonte
2
A resposta de Erwin sobre SO é ótima (e se você não se importa de copiá-la pelo @Erwin, seria útil ter aqui), mas eu gostaria de acrescentar minha própria cautela: na maioria dos casos, você não consideraria armazenar informações em cadeias de bits em um RDBMS - usando colunas booleanas separadas na solução normal, independentemente da 'eficiência' do armazenamento.
31412 Jack Douglas
@JackDouglas: Eu não me importaria de copiar minha resposta. Eu me pergunto, no entanto: duplicar uma resposta nos sites do SE é uma boa idéia?
Erwin Brandstetter
@ Erwin Eu não vejo por que não - existe alguma sobreposição entre os sites e eles devem permanecer sozinhos (por exemplo, não faríamos - e de qualquer maneira não poderíamos) fechar uma pergunta aqui como duplicada, se houver uma pergunta idêntica no SO). Nosso foco está mais em questões 'especialistas', mas IMO seus ataques de resposta que categoria, tal como está :)
Jack Douglas
@JackDouglas: Bem, faz sentido. E como eu poderia discordar depois dos elogios que você recebeu, afinal? ;)
Erwin Brandstetter

Respostas:

18

Se você tiver apenas algumas variáveis, eu consideraria manter booleancolunas separadas .

  • A indexação é fácil. Em particular, índices de expressões são fáceis.
  • As condições para consultas e indexação parcial são fáceis de escrever e ler e são significativas.
  • Uma coluna booleana ocupa 1 byte. Para apenas algumas variáveis, isso ocupa menos espaço.
  • Ao contrário das outras opções, as colunas booleanas permitem NULL valores para bits individuais, se você precisar. Você sempre pode definir colunas NOT NULLse não o fizer.

Otimizando o armazenamento

Se você tiver mais de uma mão de variáveis ​​completas, mas menos de 33, uma integercoluna poderá atendê-lo melhor. (Ou um bigintpara até 64 variáveis.)

  • Ocupa 4 bytes no disco.
  • Indexação muito rápida para correspondências exatas ( =operador).
  • A manipulação de valores individuais pode ser mais lenta / menos conveniente do que com bit stringou boolean.

Com ainda mais variáveis, ou se você deseja manipular muito os valores, ou se você não possui tabelas enormes e espaço em disco / RAM não é problema, ou se você não tem certeza do que escolher, eu consideraria bit(n)oubit varying(n) .

Exemplos

Para apenas 3 bits de informação, as booleancolunas individuais passam com 3 bytes, uma integerprecisa de 4 bytes e uma de bit string6 bytes (5 + 1).

Para 32 bits de informação, um integerainda precisa de 4 bytes, um bit stringocupa 9 bytes para o mesmo (5 + 4) e as booleancolunas ocupam 32 bytes.

Leitura adicional

Erwin Brandstetter
fonte
Sim, eu concordo com você. Atualmente, estou usando o samllint para armazenar a máscara de bits dos dias da semana. Adequou-se ao caso, com eficiência de armazenamento / desempenho amplo. No entanto, se eu tiver um pouco mais de indexação / filtragem em máscaras de bits, ele falhará devido ao baixo desempenho.
Jackey Cheung
3

Todos os tipos de PostgreSQL são úteis para algumas coisas e menos úteis para outras. Em geral, você se preocupa mais com a funcionalidade primeiro e o desempenho posteriormente. O PostgreSQL possui um grande número de funções para manipular vários tipos de dados, e essas não são exceções.

Eu esperaria na camada de aplicativo, a menos que o driver db lide com algum tipo de conversão de tipo, você obterá uma representação de string e precisará lidar com isso. Portanto, pode ou não ser útil nessa capacidade.

Onde provavelmente é útil é quando você deseja selecionar registros com base em operações bit a bit, como bit a bit ou ou bit a bit e, ou manipular os dados nas consultas SQL. A menos que você esteja fazendo isso, muitos dos recursos mais esotéricos do PostgreSQL são menos úteis.

Observe também que, para cadeias mais longas de informações binárias, existe uma grande interface de objeto que permite fazer streaming etc., e uma interface bytea que permite uma representação mais compacta de cadeias.

tl; dr: Se você precisar, você saberá. Caso contrário, arquive-o na seção "reservado para uso futuro" da sua mente.

Chris Travers
fonte