lightdb中extra_float_digits参数可以用来控制浮点数输出的精度,其采用原生c语言的float4/float8实现,可能我们在平时使用中并不太会留意,但是显示的时候会有一些问题。
建一张表,两个字段类型分别是float和numeric,然后插入数据,如下:
zjh@postgres=>create table t1(c1 float,c2 numeric); CREATE TABLEzjh@postgres=>insert into t1 values(0.55555555555555555,0.55555555555555555); INSERT 0 1
接下来我们去查询,你就会发现查出来的数据竟然和我们插入的不一样了!
zjh@postgres=>select * from t1; c1 | c2 -------------------+--------------------- 0.555555555555556 | 0.55555555555555555 (1 row)
好像这样看上去并没有什么,但是会很容易给我们产生误导,让你以为c1字段插入的值是0.555555555555556,其实并不是。可以看到下面的查询并没有记录。
zjh@postgres=>select * from t1 where c1 >= 0.555555555555556; c1 | c2 ----+---- (0 rows)
这是为什么呢?其实表中存的数据还是原先的0.55555555555555555,只是显示出来错误了,所以我们要这样去查询:
zjh@postgres=>select * from t1 where c1::numeric >= 0.555555555555556; c1 | c2 -------------------+--------------------- 0.555555555555556 | 0.55555555555555555 (1 row)
所以这种情况下我们就特别需要注意float类型的精度了!
接下来我们言归正传,看看extra_float_digits这个参数。
介绍这个参数前,我们需要知道在pg中float4默认精确到6位数字,float8精确到15位数字,这也是和大多数平台是一样的。
zjh@postgres=>select 12.23333333333333::float(24); float4 --------- 12.2333 (1 row) zjh@postgres=>select 12.23333333333333::float(25); float8 ------------------ 12.2333333333333 (1 row)
这里要注意下,float()中的数字并不表示精度,而是表示存储浮点数的比特位数。而且在lightdb中这个值并没有意义,只是用来区分它是float4还是float8而已。在pg中1到24个比特位表示float4,25到53个比特位表示float8。
而要控制float类型的精度便是需要通过extra_float_digits参数了。
extra_float_digits取值范围为-15~3,默认是0。等于0时float4精确到6位数字,float8精确到15位数字。增大该值则会增加精确的位数,减小则会降低精度,例如设置该值为3,则float4精确到9位数字。
–float4类型:
zjh@postgres=>do zjh-# $$ zjh$# declare i int; zjh$# begin zjh$# for i in -15..3 loop zjh$# perform set_config('extra_float_digits',i::text, 'true'); zjh$# raise notice 'extra_float_digits = %, result = %', i, 1.333333333333333::float(24); zjh$# end loop; zjh$# end; zjh$# $$language plpgsql; NOTICE: extra_float_digits = -15, result = 1 NOTICE: extra_float_digits = -14, result = 1 NOTICE: extra_float_digits = -13, result = 1 NOTICE: extra_float_digits = -12, result = 1 NOTICE: extra_float_digits = -11, result = 1 NOTICE: extra_float_digits = -10, result = 1 NOTICE: extra_float_digits = -9, result = 1 NOTICE: extra_float_digits = -8, result = 1 NOTICE: extra_float_digits = -7, result = 1 NOTICE: extra_float_digits = -6, result = 1 NOTICE: extra_float_digits = -5, result = 1 NOTICE: extra_float_digits = -4, result = 1.3 NOTICE: extra_float_digits = -3, result = 1.33 NOTICE: extra_float_digits = -2, result = 1.333 NOTICE: extra_float_digits = -1, result = 1.3333 NOTICE: extra_float_digits = 0, result = 1.33333 NOTICE: extra_float_digits = 1, result = 1.3333334 NOTICE: extra_float_digits = 2, result = 1.3333334 NOTICE: extra_float_digits = 3, result = 1.3333334 DO
–float8类型:
zjh@postgres=>do zjh-# $$ zjh$# declare i int; zjh$# begin zjh$# for i in -15..3 loop zjh$# perform set_config('extra_float_digits',i::text, 'true'); zjh$# raise notice 'extra_float_digits = %, result = %', i, 1.333333333333333::float(25); zjh$# end loop; zjh$# end; bill$# $$language plpgsql; NOTICE: extra_float_digits = -15, result = 1 NOTICE: extra_float_digits = -14, result = 1 NOTICE: extra_float_digits = -13, result = 1.3 NOTICE: extra_float_digits = -12, result = 1.33 NOTICE: extra_float_digits = -11, result = 1.333 NOTICE: extra_float_digits = -10, result = 1.3333 NOTICE: extra_float_digits = -9, result = 1.33333 NOTICE: extra_float_digits = -8, result = 1.333333 NOTICE: extra_float_digits = -7, result = 1.3333333 NOTICE: extra_float_digits = -6, result = 1.33333333 NOTICE: extra_float_digits = -5, result = 1.333333333 NOTICE: extra_float_digits = -4, result = 1.3333333333 NOTICE: extra_float_digits = -3, result = 1.33333333333 NOTICE: extra_float_digits = -2, result = 1.333333333333 NOTICE: extra_float_digits = -1, result = 1.3333333333333 NOTICE: extra_float_digits = 0, result = 1.33333333333333 NOTICE: extra_float_digits = 1, result = 1.333333333333333 NOTICE: extra_float_digits = 2, result = 1.333333333333333 NOTICE: extra_float_digits = 3, result = 1.333333333333333 DO
在lt_dump时加上 --extra-float-digits选项,用来控制导出的数据中float的精度,例如:
lt_dump -d postgres -t ttest --inserts --extra-float-digits -12 -f ttest_1219.txt
-- Data for Name: t5; Type: TABLE DATA; Schema: public; Owner: bill -- INSERT INTO public.t5 VALUES (1.23); INSERT INTO public.t5 VALUES (1.24); INSERT INTO public.t5 VALUES (1.57);
参考链接:
http://www.light-pg.com/docs/lightdb/13.8-22.3/runtime-config-client.html#RUNTIME-CONFIG-CLIENT-FORMAT
http://www.light-pg.com/docs/lightdb/13.8-22.3/datatype-numeric.html