Pergunta

Eu estou trabalhando em um projeto onde eu preciso para lidar no nível de byte com inteiros. Desde economia de espaço é uma consideração primária, eu só preciso muito pequenas (e variáveis ??ints de comprimento).

Existe uma maneira que eu posso transformar o int '4096' em 3 bytes? ou '1053' em um 2 bytes?

Obviamente eu CNA fazê-lo manualmente = (byte [0] * 256) + (byte [1]), mas eu queria saber se existe uma opção mais fácil para converter o int em x bytes e vice-versa?

Foi útil?

Solução

Você pode? Certo. Será que vai salvar qualquer espaço? Talvez, dependendo da quantidade de trabalho que você quer fazer. Você tem que entender que o processador é de 32 bits, o que significa que tem 4 registros byte, então é assim que ele vai querer armazenar e coisas de acesso. Para forçar um "int"-byte 3 você vai ter que mantê-lo em um array de bytes, e extraí-lo a partir da matriz para um endereço alinhado antes do uso. Isso significa que se você armazená-lo curto, o compilador quer pad-lo (e você vai perder qualquer eficiência que você acha que você criou) ou ele vai ser um muito mais lento para ler e escrever.

Se este é um aplicativo de desktop, como exatamente é economia de espaço a principal consideração, especialmente quando se fala 1 byte por elemento? A pena perf para acesso elemento pode mudar se importa sobre como crítico que um byte é.

Eu diria que, se que 1 byte é verdadeiramente importante, que talvez, apenas talvez, você está usando o idioma errado de qualquer maneira. O número de bytes que você salvar o meu não instalar e usar o CLR em primeiro lugar é uma muito desses bytes.

Nota lateral:. Você também faria uma mudança, não uma multiplicação (embora o compilador provavelmente chegar lá para você)

Outras dicas

Apenas para a loucura adicionado, vamos fazê-lo em C # usando o truque de estilo C união velho:

[StructLayout(LayoutKind.Explicit)]
struct OddUnion
{
    /* The 32-bit integer value */
    [FieldOffset(0)]
    public int IntegerValue;

    /* The bytes that overlap with it */
    [FieldOffset(0)]
    public byte Byte1;
    [FieldOffset(1)]
    public byte Byte2;
    [FieldOffset(2)]
    public byte Byte3;
    [FieldOffset(3)]
    public byte Byte4;
 }

E então, quando você quer "Convert", faça o seguinte:

OddUnion myOddUnion;
myOddUnion.IntegerValue = 4096;
Byte secondByte = myOddUnion.Byte1;

Mas isso realmente só ajuda se você estiver olhando para "salvar" o custo do bit de mudança de um único byte de uma palavra. Eu não olhei para o SMIL gerado, então eu não sei se este é mais barata em comparação com qualquer outra solução.

Você poderia fazer a codificação comprimento inteiro variável. O método de idade de anos atrás era usar o bit de cada byte para indicar que o número inteiro continua a outro byte. Então, você perde um pouco por byte, mas ganhar inteiros pequenos. Isto é principalmente útil no armazenamento persistente, onde cada último byte conta.

Exemplo: Suponha que estamos a lidar com números inteiros sem sinal, teríamos

int  binary
0                       00000000
1                       00000001
...  
127                     01111111
128            00000001 10000000
129            00000001 10000001
...
255            00000001 11111111
256            00000010 10000000
...
16383          01111111 11111111
16384 00000001 10000000 10000000 

para 0-127 take 1 byte e 128-16383 leva 2 bytes, etc ...

Para formas mais complexas de se fazer isso check-out desta página

BitConverter.GetBytes você irá obter os bytes.

e

BitConverter.ToInt32 vai te dar um int de 32 bits dos bytes.

Você tem que fazer alguma mudança bit. É muito mais fácil se você trabalhar com HEX, uma vez que cada número (quero dizer, todos os dígitos, mas dígito é de base 10, hex git) representam quatro bits.

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