我有一个perl脚本,可以将Excel XLS文件中的数据加载到数据库中。首先,它检查文件中值的日期时间是否已存在于数据库中。如果是,则检查文件中的值是否与数据库中的值相同。如果它们相同,则跳过该值。如果它们不同,则更新数据库中的值。
进行比较的代码是:
if($dbVal != $fileVal) {
&UpdateData($id, $dt, $fileVal);
}
问题在于,有时,即使两个值“看起来”相同,比较也会确定它们不是,并且执行更新子。以下是调试日志的摘录。对于文件中的每个值,它都会输出db值和文件值。如果执行更新子程序,则会打印“正在更新...”行:
dbVal = '68800812'; file val = '68800812'
dbVal = '66649164'; file val = '66649164'
Updating: 41248 : 01/01/2011 07:00 : 66649164
dbVal = '64975681'; file val = '64975681'
dbVal = '64037179'; file val = '64037179'
dbVal = '64095165'; file val = '64095165'
dbVal = '64917078'; file val = '64917078'
dbVal = '66584188'; file val = '66584188'
Updating: 41248 : 01/01/2011 12:00 : 66584188
所以在上面的代码片段中,有两个实例,其中db val和文件val看起来相同,但是无论如何都执行了update sub,这意味着当它看起来应该是false时,比较返回true。
任何想法/想法?
戴夫
答案 0 :(得分:3)
Devel :: Peek显示标量类型NV(浮点数)而不是预期的IV(整数)。 sprintf
显示不精确,请参阅Why am I getting long decimals (eg, 19.9499999999999) instead of the numbers I should be getting (eg, 19.95)?。当简单地打印或在字符串上下文中使用时,该数字被强制转换为具有16位尾数的表示(如果使用指数表示法则为20-21)。
在进行比较之前,对数字进行明确的舍入,sprintf
和Math::Round是合适的。
答案 1 :(得分:0)
也许你的值被视为字符串,而且两者在开头/结尾都有一个额外的空格。
试试这个:
if($dbVal - $fileVal != 0) {
&UpdateData($id, $dt, $fileVal);
}