我的初衷是将有符号的基本数字转换为它的十六进制表示方式,同时保留数字的符号。但事实证明,当前有关带符号的基本整数的 LowerHex
、UpperHex
及其相关实现只会将它们视为无符号整数来处理。无论我添加了哪些额外的格式化标志,这些实现似乎都会将数字重新解释为其无符号对应项进行格式化。(Playground)
println!("{:X}", 15i32); // F
println!("{:X}", -15i32); // FFFFFFF1 (expected "-F")
println!("{:X}", -0x80000000i32); // 80000000 (expected "-80000000")
println!("{:+X}", -0x80000000i32); // +80000000
println!("{:+o}", -0x8000i16); // +100000
println!("{:+b}", -0x8000i16); // +1000000000000000
在
std::fmt
文档中并没有明确说明这是否应该发生,或者是否有效,而且UpperHex
(或任何其他格式化特性)也没有提到有符号整数的实现将数字解释为无符号数。Rust的GitHub仓库中似乎也没有相关问题。(附加通知:从1.24.0
开始,文档已经得到改进,以正确处理这些问题,请参见问题#42860)最终,可以实现特定任务的特定函数(如下),但不幸的是,它们与格式化程序API的兼容性不是很好。
fn to_signed_hex(n: i32) -> String {
if n < 0 {
format!("-{:X}", -n)
} else {
format!("{:X}", n)
}
}
assert_eq!(to_signed_hex(-15i32), "-F".to_string());
这种有符号整数类型的行为是故意的吗?在遵循标准
Formatter
的情况下,有没有一种方法执行此格式化过程?请注意保留HTML标记。
flags()
一直存在,只是“哪个位代表什么”并没有真正记录下来... - Francis Gagné