简体   繁体   English

如何在C ++中从字节数组中的整数转换数字

[英]how to convert digits from a integer in a byte array in C++

i tried to convert the digits from a number like 9140 to a char array of bytes, i finally did it, but for some reason one of the numbers is converted wrong. 我试图将数字从9140这样的数字转换为char字节数组,但我最终做到了,但是由于某种原因,其中一个数字转换错误。

The idea is separate each digit an convert it in a byte[4] and save it a global array of bytes, that means that array have a digit each 4 positions, i insert each digit at the end of array and finally i insert the amount of digits at the end of the array. 这个想法是将每个数字分开,然后将其转换为字节[4],然后将其保存为一个全局字节数组,这意味着该数组在每个4个位置上都有一个数字,我将每个数字插入到数组的末尾,最后插入一个数字数组末尾的位数。

the problem is randomly with some values, for example for the value 25 it works but for 9140 it return me 9040, which could be the problem? 问题是随机存在一些值,例如,它可以使用值25,但对于9140,它会返回9040,这可能是问题所在? this is the code: 这是代码:

void convertCantToByteArray4Digits(unsigned char *bufferDigits,int cant){
    //char bufferDigits[32];
    int bufferPos=20;
    double cantAux=cant;
    int digit=0,cantDigits=0;
    double subdigit=0;
    while(cantAux > 0){
        cout<<"VUELTA"<<endl;
        cantAux/=10;
        cout<<"cantAux/=10:"<<cantAux<<endl;
        cout<<"floor"<<floor(cantAux)<<endl;
        subdigit=cantAux-floor(cantAux);
        cout<<"subdigit"<<subdigit<<endl;
        digit=static_cast<int>(subdigit*10);
        cout<<"digit:"<<subdigit*10<<endl;
        cantAux=cantAux-subdigit;
        cout<<"cantAux=cantAux-subdigit:"<<cantAux<<endl;
        bufferDigits[bufferPos-4] = (digit >> 24) & 0xFF;
        std::cout<<static_cast<int>(bufferDigits[bufferPos-4])<<std::endl;
        bufferDigits[bufferPos-3] = (digit >> 16) & 0xFF;
        std::cout<<static_cast<int>(bufferDigits[bufferPos-3])<<std::endl;
        bufferDigits[bufferPos-2] = (digit >> 8) & 0xFF;
        std::cout<<static_cast<int>(bufferDigits[bufferPos-2])<<std::endl;
        bufferDigits[bufferPos-1] = (digit) & 0xFF;
        std::cout<<static_cast<int>(bufferDigits[bufferPos-1])<<std::endl;
        /*bufferDigits[0] = digit >> 24;
        std::cout<<bufferDigits[0]<<std::endl;
        bufferDigits[1] = digit >> 16;
        bufferDigits[2] = digit >> 8;
        bufferDigits[3] = digit;*/
        bufferPos-=4;
        cantDigits++;
    }
    cout<<"sizeof"<<sizeof(bufferDigits)<<endl;
    cout<<"cantDigits"<<cantDigits<<endl;
    bufferPos=24;
    bufferDigits[bufferPos-4] = (cantDigits) >> 24;
        //std::cout<<bufferDigits[bufferPos-4]<<std::endl;
    bufferDigits[bufferPos-3] = (cantDigits) >> 16;
    bufferDigits[bufferPos-2] = (cantDigits) >> 8;
    bufferDigits[bufferPos-1] = (cantDigits);

}

the bufferDigits have a size of 24 bytes, the cant parameter is the number to convert, i receive any question about my code. bufferDigits的大小为24个字节,cant参数是要转换的数字,我收到有关我的代码的任何问题。

I feel this is the most c++ way that probably answers your question, if I understood correctly: 如果我理解正确,我认为这是最可能回答您问题的C ++方法:

#include <string>
#include <iterator>
#include <iostream>
#include <algorithm>

template <typename It>
It tochars(unsigned int i, It out)
{
    It save = out;

    do    *out++ = '0' + i%10;
    while (i/=10);

    std::reverse(save, out);
    return out;
}

int main()
{
    char buf[10];

    char* end = tochars(9140, buf);
    *end = 0; // null terminate

    std::cout << buf << std::endl;
}

Instead of using a double and the floor function, just use an int and the modulus operator instead. 代替使用double和floor函数,只需使用int和模数运算符即可。

void convertCantToByteArray4Digits(unsigned char *bufferDigits,int cant)
{
  int bufferPos=20;
  int cantAux=cant;
  int digit=0,cantDigits=0;
  while(cantAux > 0)
  {
    cout<<"VUELTA"<<endl;
    digit = cantAux % 10;
    cout<<"digit:"<<digit<<endl;
    cantAux /= 10;
    cout<<"cantAux/=10:"<<cantAux<<endl;
    bufferDigits[bufferPos-4] = (digit >> 24) & 0xFF;
    std::cout<<static_cast<int>(bufferDigits[bufferPos-4])<<std::endl;
    bufferDigits[bufferPos-3] = (digit >> 16) & 0xFF;
    std::cout<<static_cast<int>(bufferDigits[bufferPos-3])<<std::endl;
    bufferDigits[bufferPos-2] = (digit >> 8) & 0xFF;
    std::cout<<static_cast<int>(bufferDigits[bufferPos-2])<<std::endl;
    bufferDigits[bufferPos-1] = (digit) & 0xFF;
    std::cout<<static_cast<int>(bufferDigits[bufferPos-1])<<std::endl;
    bufferPos-=4;
    cantDigits++;
  }

Why not use a union? 为什么不使用工会呢?

union {
  int i;
  char c[4];
};

i = 2530;
// now c is set appropriately

Or memcpy? 还是memcpy?

memcpy(bufferDigits, &cant, sizeof(int));

Why so complicated? 为什么这么复杂? Just divide and take remainders. 只需除以余数即可。 Here's a reentrant example to which you provide a buffer, and you get back a pointer to the beginning of the converted string: 这是一个可重入的示例,在该示例中提供了缓冲区,并获得了指向转换后的字符串开头的指针:

char * to_string(unsigned int n, char * buf, unsigned int len)
{
  if (len < 1) return buf;

  buf[--len] = 0;

  if (n == 0 && len > 0) { buf[--len] = '0'; }

  while (n != 0 && len > 0) { buf[--len] = '0' + (n % 10); n /= 10; }

  return &buf[len];
}

Usage: char buf[100]; char * s = to_string(4160, buf, 100); 用法: char buf[100]; char * s = to_string(4160, buf, 100); char buf[100]; char * s = to_string(4160, buf, 100);

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM