场景

  1. 在开发使用加密算法md5,sha256等的功能时, 会生成基于十六进制的字符串密钥。 这时候在使用这些密钥进行解密或加密的时候,第三方库都需要传入一个字节数组usigned char*格式的数组,它每个字节的高4位和低4位都分别存储了1个字符值。那么用C++如何实现?

说明

  1. 举例子比如字符串"a3fd",它有4个字符,那么它实际上只需要2个字节就可以存储。每两个字符存储在一个字节里,分别对应着高低4位。所以"a3fd"就是在内存里的结果是{0xa3,0xfd}

  2. 如果是使用python的话,bytes类型的对象默认就有fromhex方法,很方便,可惜C++标准库没有这么方便的方法。

    bytes.fromhex(strData)
    
  3. 我们知道标准字符串string可以存储任意的字节数据0~0xff, 它的size()并不是遇到\0就会结束。所以可以使用string来存储字节数组。

  4. C++11<string>里,增加了一个std::stoi方法,用来把字符串转换为对应的int值,也就是之前说的十六进制转换。 使用它来转换两个字符到int值,再把这个uint8_t值添加到作为字节数组存储的string里即可。

    int stoi( const std::string& str, std::size_t* pos = 0, int base = 10 );
    
  5. 注意,这里的十六进制字符串必须是偶数个,如果是奇数个,那么最有一个字符就不清楚是放在高位还是低位。

例子

  1. 这里分别用C++11C++98实现了转换的方法。如果是逆转过来,把字节数组转换为十六进制字符串,只需要使用stringstream作为输入或者sprintf "%.x"即可,参考ConvertBytesToEvenHexString()函数.
// test-hex-string-to-byte.cpp : 定义控制台应用程序的入口点。
//#include "stdafx.h"
#include <string>
#include <stdint.h>
#include <iostream>
#include <assert.h>
#include <sstream>
#include <math.h>using namespace std;// https://blog.csdn.net/infoworld/article/details/9451591
static uint8_t stoi98(const string& data)
{auto& first = data[0];uint8_t f = (first & 0x40)?(first&0x0F)+0x9:(first & 0x0F);auto& second = data[1];uint8_t s = (second & 0x40)?(second&0x0F)+0x9:(second & 0x0F);return ((f << 4) & 0xf0) | (s & 0x0f);
}static string ConvertEvenHexStringToBytesCpp11(const string& data)
{string result;auto size = data.size();auto count = size / 2;for(size_t i = 0; i< count; i++){auto value = (uint8_t)stoi(data.substr(i*2,2),0,16);result.append(1,value);}return result;
}static string ConvertEvenHexStringToBytesCpp98(const string& data)
{string result;auto size = data.size();auto count = size / 2;for(size_t i = 0; i< count; i++){auto sub = data.substr(i*2,2);auto value = (uint8_t)stoi98(sub.c_str());result.append(1,value);}return result;
}static string ConvertBytesToEvenHexString(const string& data)
{stringstream ss;ss << hex;for(size_t i = 0; i< data.size(); ++i){auto& one = data[i];ss << (one >> 4 & 0x0f) << (one & 0x0f);}string result = ss.str();return result;
}int _tmain(int argc, _TCHAR* argv[])
{auto str = "a3fd";auto result = ConvertEvenHexStringToBytesCpp11(str);auto mResult = "\xa3\xfd";assert(result.size() == (strlen(str) /2) );assert(result == mResult);auto source = ConvertBytesToEvenHexString(result);cout << source << endl;assert(str == source);str = "a3fd7be21c504d8ed7d19b";result = ConvertEvenHexStringToBytesCpp11(str);mResult = "\xa3\xfd\x7b\xe2\x1c\x50\x4d\x8e\xd7\xd1\x9b";assert(result.size() == (strlen(str) /2));assert(result == mResult);source = ConvertBytesToEvenHexString(result);cout << source << endl;assert(str == source);str = "a3fd";result = ConvertEvenHexStringToBytesCpp98(str);mResult = "\xa3\xfd";assert(result.size() == (strlen(str) /2));assert(result == mResult);source = ConvertBytesToEvenHexString(result);cout << source << endl;assert(str == source);str = "a3fd7be21c504d8ed7d19b";result = ConvertEvenHexStringToBytesCpp98(str);mResult = "\xa3\xfd\x7b\xe2\x1c\x50\x4d\x8e\xd7\xd1\x9b";assert(result.size() == (strlen(str) /2));assert(result == mResult);source = ConvertBytesToEvenHexString(result);cout << source << endl;assert(str == source);system("pause");return 0;
}

输出

a3fd
a3fd7be21c504d8ed7d19b
a3fd
a3fd7be21c504d8ed7d19b

参考

  1. 十六进制字符串转换数值并写入文件

  2. 输出内存数据的二进制和十六进制的字符串表示

  3. 使用zlib库压缩和解压字符串STL string

  4. C++11语言特性和标准库-第一部-infoworld的课程

[C++11]_[初级]_[十六进制字符串转换为字节数组]相关推荐

  1. scala 字符串转换数组_如何在Scala中将十六进制字符串转换为字节数组?

    scala 字符串转换数组 Hex String in Scala denotes value in hexadecimal number system i.e. base 16 number sys ...

  2. 十六进制字符串转换为字节数组

    第一步.将十六进制的字符串除以二,算出字节数组的长度: 第二步.根据字节数组的长度,创建字节数组: 第三步.将字符串转换为字符数组: 第四步.将字符转换为字节: 第五步.十六进制的字节分为高四位与低四 ...

  3. c#中将整数转化为字符串_在C#中将字符串转换为字节数组

    c#中将整数转化为字符串 Prerequisite: How to declare and use byte[] in C#? 先决条件: 如何在C#中声明和使用byte []? C#中的字符串到字节 ...

  4. 十六进制字符串与字节数组的转换

    十六进制字符串与字节数组的转换 十六进制(hex):0-9,A-F组成,不区分大小写,与十进制对应关系:0-9对应0-9,A-F对应10-15 位(bit):java语言中1个bit  用0或1表示 ...

  5. 在C#中将字符串转换为字节数组

    本文翻译自:Converting string to byte array in C# I'm converting something from VB into C#. 我正在将某些东西从VB转换为 ...

  6. JavaScript:实现将 base64 字符串转换为字节数组算法(附完整源码)

    JavaScript:实现将 base64 字符串转换为字节数组算法 function base64ToBuffer (b64) {// The base64 encoding uses the fo ...

  7. 十六进制字符串与字节数组转换工具

    1.十六进制字符串转字节数组 public static byte[] hexToBytes(String hex) {hex = hex.length() % 2 != 0 ? "0&qu ...

  8. c#将字符串转换为数组,在C#中将字符串转换为字节数组

    先决条件:如何在C#中声明和使用byte []? C#中的字符串到字节数组的转换 在C#中,可以使用Encoding将字符串转换为字节数组.方法,它接受字符串作为参数并返回字节数组.ASCII.Get ...

  9. java字符串转换成字节数组_将Java字符串转换为字节数组

    我有一个要加密的字节数组,然后转换为字符串,以便可以传输. 当我收到字符串时,我必须将字符串转换回字节数组,以便可以对其进行解密. 我检查了接收到的字符串是否与发送的字符串(包括长度)匹配,但是当我使 ...

最新文章

  1. 从硬盘上装xp手记(2005.8.14 )
  2. Leetcode 240.搜索二维矩阵II (每日一题 20210727 同一题)
  3. linux watch 文件大小,Linux watch命令的使用
  4. 阿里云周源:一篇文章读懂四代视频加密技术演进
  5. POJ3628:Bookshelf 2【01背包】
  6. Discuz! X3.2后台管理员登录不了的问题
  7. 11.15PMP试题每日一题
  8. 一个算例 介绍 libmesh 的类
  9. Exchange 2013 OU大于500新建用户无法查询OU
  10. python3使用smtplib通过qq邮箱发送邮件
  11. linux如何入侵电脑,Linux超大漏洞,按28次Backspace键即可入侵电脑
  12. 倾斜摄影OSGB转换为3DTiles
  13. Hadoop,Hive和Spark大数据框架的联系和区别
  14. springboot为什么返回Whitelabel Error Page
  15. 苹果手机sim卡无效怎么办_苹果手机解锁密码忘了怎么办
  16. 个人博客处理——页面处理
  17. 电路原理实验八:受控源特性测试
  18. 容器PaaS资源导航
  19. matlab函数变量名替换,matlab替换符号函数的自变量
  20. 【雷达与对抗】【2012.12】基于脉冲多普勒雷达的行走检测

热门文章

  1. linux番茄时钟,Linux 番茄时钟 定时 取消 快捷方式
  2. 工作22年后明白的22条职场道理
  3. 基于HTML和css的静态网页仿写
  4. Hadoop HA HDFS启动 NameNode启动失败解析
  5. 电源管理芯片:LED驱动电源芯片的计划及面积
  6. JSON数据里提取tracks里name的内容
  7. uA741运算放大器原理
  8. 基于matlab的bp神经网络,基于MATLAB的BP神经网络建模及系统仿真 (1)
  9. 法坤老师:法坤电子书搜索系统搭建
  10. Facebook身份验证如何有效通过