我正在尝试使用xlrd模块将excel(xlsx)文件中的数据转储到文本文件中,并且浮动进程存在问题。
已找到一些类似问题的帖子,在16位十进制数字的最后一位丢失岁差。
以下是从xlsx复制的数据:
VALUE;DATA
1.01 HELLO
2.11 1/1/2014
3.21 ONE
4.31 1/1/2014 12:14
5.441 $10
6.241 TWO
77.11 Zulfi
8.11 99
9.11 99.999
10.11 0
以下是我从xlrd获得的信息:
1.01|'HELLO'
2.1099999999999999|'2014-01-01 00:00:00.000000'
3.21|'ONE'
4.3099999999999996|'2014-01-01 12:14:00.000000'
5.4409999999999998|10.0
6.2409999999999997|'TWO'
77.109999999999999|'Zulfi'
8.1099999999999994|99.0
9.1099999999999994|99.998999999999995
10.109999999999999|0.0
我确实理解浮游物的一些奥秘,其中有可能失去进动,因为小数点后面有太多数字的值,但这里我只有两位数。
我通过与开源ETL工具" Pentaho"的比较来测试输出。 (用java编写)可以读取/写入excel文件,这个工具似乎没有问题,因为它们出现在xlsx文件中(这些字段被读作字符串和长度为30且进动数为20的数字)
以下是Pentaho的内容
VALUE;DATA
1.01;HELLO
2.11;2014/01/01 00:00:00.000
3.21;ONE
4.31;2014/01/01 12:14:00.000
5.441; 10.0
6.241;TWO
77.11;Zulfi
8.11; 99.0
9.11; 99.999
10.11; 0.0
以下是我的python代码:
for rownum in xrange(sh.nrows):
for colnum in xrange(sh.ncols):
cell_obj = sh.cell(rownum,colnum)
cell_val=sh.cell_value(rownum,colnum)
if cell_obj.ctype == xlrd.XL_CELL_DATE:
year, month, day, hour, minute, second = xlrd.xldate_as_tuple(cell_val, wb.datemode)
py_date = datetime.datetime(year, month, day, hour, minute, second).strftime("%Y-%m-%d %H:%M:%S.%f")
cell_val = py_date
if (colnum==0):
row_values=repr(cell_val)
else :
row_values=row_values+fdel+repr(cell_val)
if (((row_values).find("\\n"))>-1):
NLFlag=1
file_output.write((row_values).replace('\\n','') + "\n")
row_values=''
file_output.close()
对此的任何帮助都非常感谢。
由于
答案 0 :(得分:0)
Floats,又名双精度实数,只有大约16个十进制数字的精度。当分数的形式为2 ^ -n时,它们只能精确地表示小数分数,因此是1/8或1/1024的倍数。所有其他小数可能不准确。
如果您打印出没有进一步说明的浮动,您将获得系统尽力表示十进制的二进制分数,所以2.099999999999等而不是2.1。但是,如果您知道浮点数不超过(例如)3个十进制数字,那么您可以强制它们在输出上舍入,例如通过使用字符串格式函数
file_output.write('{0:.3f}'.format(f_num))
将正确向下舍入输出f_num并用零填充到3个位置
我猜想默认情况下,xlrd库会解释任何可以作为float的字段。应该有一个开关强制所有的读取都是字符串,在这种情况下,你打印出来的内容就是你所读的内容。