在我们的 Oracle 数据库中,我有一个表(比如 MYTABLE),其中列 VALUE_NUMBER 类型为 NUMBER(NULL,未指定精度)。此表包含一个值1178.2
当使用标准 ADO.Net(实际上是 ODP.Net)从该列中检索数据,然后将十进制值转换为字符串时,我得到“1178.20”。显然,将常量转换1178.2M
为字符串时,输出为1178.2
.
深入挖掘,我查看了 decimal.GetBits() 的输出,结果证明是不同的,尽管在比较两个数字时它们确实被认为是相等的。
下面的代码示例说明了这种行为:
using (var connection = new OracleConnection("my connection string"))
{
connection.Open();
var command = connection.CreateCommand();
command.CommandText = "SELECT VALUE_NUMBER FROM MYTABLE";
command.CommandType = CommandType.Text;
using (command)
{
var reader = command.ExecuteReader(CommandBehavior.Default);
reader.Read();
decimal oracleDecimal = reader.GetDecimal(reader.GetOrdinal("VALUE_NUMBER"));
Console.WriteLine(oracleDecimal); // output: 1178.20 (NOT expected)
var bitsFromOracle = decimal.GetBits(oracleDecimal).Select(x => x.ToString());
var bitsFromOracleString = string.Join(",", bitsFromOracle.ToArray());
Console.WriteLine(bitsFromOracleString); // 117820,0,0,131072
// sanity check
const decimal constantDecimal = 1178.2M;
Console.WriteLine(constantDecimal); // output: 1178.2 (expected)
var bitsFromConstant = decimal.GetBits(constantDecimal).Select(x => x.ToString());
var bitsFromConstantString = string.Join(",", bitsFromConstant.ToArray());
Console.WriteLine(bitsFromConstantString); // 11782,0,0,65536
Console.WriteLine(oracleDecimal == constantDecimal); // True
}
}
这应该如何解释?
下面是表 CREATE & INSERT 脚本来完成这项工作:
CREATE TABLE MYTABLE (
ID NUMBER(10) NOT NULL,
VALUE_NUMBER NUMBER
);
INSERT INTO MYTABLE(ID,VALUE_NUMBER) VALUES(1,1178.2);
更新:
@Vash 的回答和他随后的评论得出了正确的结论,即 .Net 十进制类型实际上包含有关其位数的信息,即使它们与相等性无关。1178.2M
并1178.20M
因此具有不同的位表示,尽管.Equals()
方法和==
运算符显然认为这些数字相等。