C++、Java 都在语言的语法中包含 [-]0xh.hhhhp+/-d 格式,其他语言如 python 和 C99 具有解析这些字符串的库支持(float.fromhex、scanf)。
我还没有找到用 C# 或使用 .NET 库来解析这种精确的十六进制编码指数格式的方法。
有没有一种很好的方法来处理这个问题,或者一个不错的替代编码?(十进制编码不准确)。
示例字符串:0x1p-8 -0xfe8p-12
谢谢
C++、Java 都在语言的语法中包含 [-]0xh.hhhhp+/-d 格式,其他语言如 python 和 C99 具有解析这些字符串的库支持(float.fromhex、scanf)。
我还没有找到用 C# 或使用 .NET 库来解析这种精确的十六进制编码指数格式的方法。
有没有一种很好的方法来处理这个问题,或者一个不错的替代编码?(十进制编码不准确)。
示例字符串:0x1p-8 -0xfe8p-12
谢谢
不幸的是,我不知道 .NET 内置的任何方法可以与 Python 的float.fromhex()相比。所以我想你唯一能做的就是在 C# 中滚动你自己的 .fromhex() 。此任务的难度范围从“有些简单”到“非常困难”,具体取决于您希望解决方案的完成程度和优化程度。
正式地,IEEE 754规范允许在十六进制系数内使用小数(即 0xf.e8p-12),这为我们增加了一层复杂性,因为(令我沮丧的是).NET 也不支持十六进制的 Double.Parse()字符串。
如果您可以将问题限制在您提供的示例中,其中您只有整数作为系数,您可以使用以下使用字符串操作的解决方案:
public static double Parsed(string hexVal)
{
int index = 0;
int sign = 1;
double exponent = 0d;
//Check sign
if (hexVal[index] == '-')
{
sign = -1;
index++;
}
else if (hexVal[index] == '+')
index++;
//consume 0x
if (hexVal[index] == '0')
{
if (hexVal[index+1] == 'x' || hexVal[index+1] == 'X')
index += 2;
}
int coeff_start = index;
int coeff_end = hexVal.Length - coeff_start;
//Check for exponent
int p_index = hexVal.IndexOfAny(new char[] { 'p', 'P' });
if (p_index == 0)
throw new FormatException("No Coefficient");
else if (p_index > -1)
{
coeff_end = p_index - index;
int exp_start = p_index + 1;
int exp_end = hexVal.Length;
exponent = Convert.ToDouble(hexVal.Substring(exp_start, exp_end - (exp_start)));
}
var coeff = (double)(Int32.Parse(hexVal.Substring(coeff_start, coeff_end), NumberStyles.AllowHexSpecifier));
var result = sign * (coeff * Math.Pow(2, exponent));
return result;
}
如果您正在寻找与 Python 的 fromhex() 相同的函数,您可以尝试将CPython 实现转换为 C#。我试过了,但由于我对标准不是很熟悉,并且在遵循他们正在寻找的所有溢出检查时遇到了麻烦,所以我陷入了困境。它们还允许其他内容,例如无限的前导和尾随空格,这是我的解决方案所不允许的。
我的解决方案是“有点简单”的解决方案。我猜如果你真的知道你的东西,你可以在位级别构建符号、指数和尾数,而不是把所有东西都相乘。您当然也可以一次性完成,而不是使用 .Substring() 方法作弊。
希望这至少能让你走上正轨。
我编写了 C# 代码,用于格式化和解析 IEEE 754r 中描述的十六进制浮点格式的数字,并受 C99、C++11 和 Java 的支持。该代码是 F# 的 BSD 许可FParsec库的一部分,包含在单个文件中: https ://bitbucket.org/fparsec/main/src/tip/FParsecCS/HexFloat.cs
支持的格式在http://www.quanttec.com/fparsec/reference/charparsers.html#members.floatToHexString有所描述
测试代码(用 F# 编写)可以在https://bitbucket.org/fparsec/main/src/tip/Test/HexFloatTests.fs找到