说明
- hexString是字节序是小端的(读值得时候会转为大端来读取值)
- valueByteSizes是个根据要求顺序读取值得字节大小的数组。
例如:new byte[]{4,2,1},程序会顺序读取hexString字符串:
- 第一个值取4个字节并读取其值,
- 第2个值取2个字节,
- 第3个值取1个字节,
4.(如果存在)第4个值取1个字节。
其传的字节数组不足以读取完全部的16进制字符串,将取字节数组的最后一个元素作为读取字节的大小。
public void handle(String hexString, byte[] valueByteSizes){
// 1个Byte标识2个十六进制的字符
final byte HexByte = 2;
// 小端序和大端序读取区
final ByteBuffer writeByteBufferLittleEndian = ByteBuffer.allocate(8).order(ByteOrder.LITTLE_ENDIAN);
final ByteBuffer readByteBufferBigEndian = writeByteBufferLittleEndian.asReadOnlyBuffer().order(ByteOrder.BIG_ENDIAN);;
final byte valueByteLength = (byte) valueByteSizes.length;
// 数据字符串的长度
int hexLength = hexString.length();
// 读取指针的位置,下一个的位置
int position = 0;
// 计次索引,注意,这是个索引值,从0开始
int itemIndex = 0;
// 初始字节
int valueByteSize = valueByteSizes[0];
while (position < hexLength) {
// 计算当前position + (十六进制的位数长度),代表当前值的结束位置
// position ~ posEnd,左闭右开,代表当前取16进制的字符串区间。
int posEnd = position + (byte) (valueByteSize * HexByte);
// 元素数据,需要额外的处理
String rawHexString = hexString.substring(position, posEnd);
long rawValue = Long.parseLong(rawHexString, 16);
// 经过处理转换的最终数据的值
long value;
// 如果是单字节,就不需要小端写入->大端读取
if(valueByteSize == 1){
value = rawValue;
}else{
writeByteBufferLittleEndian.putLong(rawValue);
// 根据字节大小进行不同的调用
switch (valueByteSize) {
case 1:
value = readByteBufferBigEndian.get();
break;
case 2:
value = readByteBufferBigEndian.getShort();
break;
case 4:
value = readByteBufferBigEndian.getInt();
break;
case 8:
value = readByteBufferBigEndian.getLong();
break;
default:
throw new RuntimeException("不支持此字节操作");
}
}
// System.out.printf("处理数据项 %s,%s == %s -> %s ==> %s \n", position, posEnd, rawHexString, rawValue, value);
// 返回的是下一个值所要读取的字节数
doHandle(value, itemIndex++);
/*
更新下一个值所代表的字节数,
当 valueByteLength < itemIndex 时,保留最后一次的字节数用于提取剩下的值
*/
if(itemIndex < valueByteLength) {
valueByteSize = valueByteSizes[itemIndex];
}
// 更新当前开始位置的指针
position = posEnd;
writeByteBufferLittleEndian.clear();
readByteBufferBigEndian.clear();
}
}
附加
1. base64转为16进制字符串(主要代码)
byte[] decodeValue = Base64.getDecoder().decode(value);
hexBinaryString = DatatypeConverter.printHexBinary(decodeValue);