【问题标题】:Converting unsigned char array to hex将无符号字符数组转换为十六进制
【发布时间】:2016-12-12 06:18:21
【问题描述】:

我想将 unsigned char 转换为 hex(使用 unsigned int)。到目前为止,这是我的代码。我有一个 program1 生成一个 unsigned char 数组,而另一个 program2 只接受十六进制(使用 unsigned int),所以我想要实现的是获取 unsigned char 数组的输入并将该数组转换为十六进制。

(例如,program1 输出“1234567812345678”,program2 应该输出“31323334353637383132333435363738”)

对不起,如果这个问题看起来很愚蠢。在这里四处寻找答案,但似乎不是我想要的。

uint64_t phex (unsigned char[16], long);



int main (void) {

int i;
unsigned char key[16] = "1234567812345678";


uint64_t* keyHex = phex(key,16); //store into an array here

for(i = 0; i < 16; i++)
printf("%.2x ", keyHex[i]);

free(keyHex);

return 0;

}


uint64_t phex(unsigned char* string, long len)
{

int i;
//allocate memory for your array
uint64_t* hex = (uint64_t*)malloc(sizeof(uint64_t) * len);

for(i = 0; i < len; ++i) {
    //do char to int conversion on every element of char array
    hex[i] = string[i] - '0';
}

//return integer array
return hex;

}

【问题讨论】:

  • 0x1234567812345678 十六进制是 ‭1311768465173141112‬ 十进制。我不知道你从哪里得到31323334353637383132333435363738。也许您想将二进制数据转换为十六进制字符串表示形式?
  • @BarmakShemirani 我想将 1234567812345678(十进制)转换为十六进制,即 31323334353637383132333435363738。

标签: c arrays


【解决方案1】:

如果您只需打印值,则无需进行任何转换。只需在原始数组上使用printf%.2x即可。

int main (void) {
    int i;
    unsigned char key[16] = "1234567812345678";
    for(i = 0; i < 16; i++)
        printf("%.2x", key[i]);
    return 0;
}

即使你想在其他一些函数中使用数组,key中实际存储的字节也是ascii字符,即0x310x32等,一般可以直接使用数组key

编辑:要将输出存储在字符数组中,您可以使用sprintf 函数。

char hex[33];
for(i = 0; i < 16; i++)
    sprintf(hex+2*i, "%.2x", key[i]);

还要注意原始数组 key 应该是 17 个字节,以说明末尾的 \0

【讨论】:

  • 有没有办法将输出保存为无符号整数?我的 program2 只接受 unsigned int。
【解决方案2】:

这是我的看法 - phex() 函数可转换任何数据 在内存中放入一个新分配的包含十六进制表示的字符串。

main() 函数显示了一个示例用法。对于示例data,输出为“31323334353637383930”。

#include <stdlib.h> /* malloc() */
#include <stdio.h>  /* sprintf() */
#include <string.h> /* strlen(), in the example main() */

/*
 * Return a hex string representing the data pointed to by `p`,
 * converting `n` bytes.
 *
 * The string should be deallocated using `free()` by the caller.
 */
char *phex(const void *p, size_t n)
{
    const unsigned char *cp = p;              /* Access as bytes. */
    char *s = malloc(2*n + 1);       /* 2*n hex digits, plus NUL. */
    size_t k;

    /*
     * Just in case - if allocation failed.
     */
    if (s == NULL)
        return s;

    for (k = 0; k < n; ++k) {
        /*
         * Convert one byte of data into two hex-digit characters.
         */
        sprintf(s + 2*k, "%02X", cp[k]);
    }

    /*
     * Terminate the string with a NUL character.
     */
    s[2*n] = '\0';

    return s;
}

/*
 * Sample use of `phex()`.
 */
int main(void)
{
    const char *data = "1234567890";               /* Sample data */
    char *h = phex(data, strlen(data));  /* Convert to hex string */

    if (h != NULL)
        puts(h);                                  /* Print result */

    free(h);                             /* Deallocate hex string */
    return 0;
}

【讨论】:

    【解决方案3】:

    我将函数签名视为

     uint64_t phex (unsigned char[16], long);
    

    所以我认为,您不需要 uint64_t 的数组来转换一个字符串,代表一个数字(也许我错了,您想将每个字符从其 char 表示形式转换为 int 并显示为十六进制数) .

    首先,让我们考虑下面的十进制转换代码(实际上,您的示例中的数字 - 1234567812345678 - 看起来像十进制数字):

    uint64_t phex(unsigned char* string, long len)
    {
    
        int i;
        //you do not need to allocate memory for array
        uint64_t hex = 0; // just one variable
    
        for (i = 0; i < len; ++i) {
            hex *= 10; // shift
            hex += string[i] - '0'; // add to the smallest rank
        }
    
        //return integer Value
        return hex;
    
    }
    

    那么对于十六进制程序将是:

    #include <stdio.h>
    #include <stdint.h>
    #include <string.h>
    uint64_t phex(unsigned char[16], long);
    
    int main(void) {
    
        int i;
        unsigned char key[16] = "A123B00CF1";
    
    
        uint64_t keyHex = phex(key, strlen(key));
    
        printf("%lld(dec) = %llx(hex)", keyHex, keyHex);
    
        return 0;
    }
    
    
    uint64_t phex(unsigned char* string, long len)
    {
        int i;
        uint64_t hex = 0;
        for (i = 0; i < len; ++i) {
            hex *= 0x10; // shift for one hexadecimal digit
            // -'0' for digits 0..9 and -('A'-10) for digits `A`..`F`
            hex += toupper(string[i]) - ((string[i] >= 'A') ? ('A' - 10) : '0');
            // TODO: Consider making check for characters that are not hexadecimal
            // e.g. use isxdigit(string[i]) in some if statement
        }
        return hex;
    }
    

    注意:您的示例代码中有一个错误 - uint64_t* keyHex 从返回 uint64_t 的函数中获取值(不是指针 `uint64_t*`),但如果你接受我的想法,你根本不需要指针。

    【讨论】:

      【解决方案4】:

      如果任务是将字符('1'、'2' 等)转换为它们的十六进制表示('1' 为 31,'2' 为 32 等),很难理解你为什么需要uint64_t.

      但是对于你的任务代码可以如下(不带uint64_t):

      #include <stdio.h>
      #include <string.h>
      
      unsigned int * phex(unsigned char[16], long);
      
      int main(void) {
          int i;
          unsigned char key[16] = "1234567812345678";
          unsigned* keyHex = phex(key, strlen(key)); // strlen(key) to determine number of characters 
          for (i = 0; i < 16; i++)
              printf("%.2x", keyHex[i]); // you do need space as I see from your example
          free(keyHex);
          return 0;
      
      }
      
      
      unsigned int * phex(unsigned char* string, long len)
      {
          int i;
          //allocate memory for array
          unsigned int * hex = (unsigned int *)malloc(sizeof(unsigned int) * len);
          for (i = 0; i < len; ++i) {
              //no special conversion needed
              hex[i] = string[i];
          }
          //return array with hexadecimal representation for each character in string
          return hex;
      }
      

      【讨论】:

      • 我的 program2 只接受 unsigned int。
      猜你喜欢
      • 2015-01-11
      • 1970-01-01
      • 2017-01-11
      • 2013-03-22
      • 2022-09-22
      • 2011-03-14
      • 1970-01-01
      • 1970-01-01
      • 2012-11-09
      相关资源
      最近更新 更多