如何将固定长度Vec<u8>
的十六进制字符转换为u32
?
let input: Vec<u8> = vec!['b','e','e','f']; // Pretend this works
let output: u32 = // Do some magic (Probably with serialize)
assert!(0xbeef == output);
答案 0 :(得分:4)
这可能不是最有效的方式,但可能是最明显的方式。首先将字节转换为字符串,然后将该字符串转换为数字:
Rust 1.0
fn main() {
let input: Vec<u8> = b"beef"[..].to_owned();
let s = String::from_utf8(input).unwrap();
let v = u32::from_str_radix(&s, 16).unwrap();
println!("{:x}", v);
assert!(0xbeef == v);
}
原创
use std::num;
fn main() {
let input: Vec<u8> = vec!['b' as u8, 'e' as u8, 'e' as u8, 'f' as u8];
let s = String::from_utf8(input).unwrap();
let v: u32 = num::from_str_radix(&*s, 16).unwrap();
println!("{:x}", v);
assert!(0xbeef == v);
}
有没有办法用
serialize
执行此操作?
不是我知道的。序列化具有FromHex
,可将&str
转换为Vec<u8>
。那么你仍然必须以某种方式将这些字节转换为数字:
extern crate serialize;
use serialize::hex::FromHex;
fn main() {
let input: Vec<u8> = vec!['b' as u8, 'e' as u8, 'e' as u8, 'f' as u8];
let s = String::from_utf8(input).unwrap();
let bytes: Vec<u8> = s.from_hex().unwrap();
let v = bytes.into_iter().fold(0u32, |val, byte| val << 8 | byte as u32);
println!("{:x}", v);
assert!(0xbeef == v);
}
此时,将代码点直接转换为数字并自行完成总结可能更容易:
fn dehex(c: u8) -> u8 {
match c {
b'0'...b'9' => c - b'0',
b'a'...b'f' => c - b'a' + 10,
b'A'...b'F' => c - b'A' + 10,
_ => panic!("Do something better here"),
}
}
fn main() {
let input: Vec<u8> = vec![b'b', b'e', b'e', b'f'];
let v = input.into_iter().fold(0u32, |val, char| (val << 4) | dehex(char) as u32);
println!("{:x}", v);
assert!(0xbeef == v);
}