我通过红宝石宝石“的续集”使用PostgreSQL。
我试图四舍五入至小数点后两位。
这里是我的代码:
SELECT ROUND(AVG(some_column),2)
FROM table
我得到以下错误:
PG::Error: ERROR: function round(double precision, integer) does
not exist (Sequel::DatabaseError)
我得到的,当我运行下面的代码没有错误:
SELECT ROUND(AVG(some_column))
FROM table
有谁知道我做错了吗?
PostgreSQL不限定round(double precision, integer)
。 至于原因,@Catcall解释了评论,圆,需要一个精确的版本仅适用于numeric
。
regress=> SELECT round( float8 '3.1415927', 2 );
ERROR: function round(double precision, integer) does not exist
regress=> \df *round*
List of functions
Schema | Name | Result data type | Argument data types | Type
------------+--------+------------------+---------------------+--------
pg_catalog | dround | double precision | double precision | normal
pg_catalog | round | double precision | double precision | normal
pg_catalog | round | numeric | numeric | normal
pg_catalog | round | numeric | numeric, integer | normal
(4 rows)
regress=> SELECT round( CAST(float8 '3.1415927' as numeric), 2);
round
-------
3.14
(1 row)
(在上面,注意float8
仅仅是一个速记别名double precision
。你可以看到,是PostgreSQL扩展它的输出)。
你必须转换为四舍五入到值numeric
使用的双参数形式round
。 只是追加::numeric
的简写投,像round(val::numeric,2)
如果你格式化以显示给用户,不要用round
。 使用to_char
(参见: 数据类型格式化功能手册中),它可以让你指定格式,并为您提供了一个text
未受到任何怪事你的客户端语言可能会做的结果numeric
值。 例如:
regress=> SELECT to_char(float8 '3.1415927', 'FM999999999.00');
to_char
---------------
3.14
(1 row)
to_char
将圆号码,你作为格式的一部分。 在FM
前缀告诉to_char
,你不想与前导空格任何填充。
也尝试旧的语法铸造,
SELECT ROUND(AVG(some_column)::numeric,2)
FROM table;
PostgreSQL的任何版本的作品。
有一些PostgreSQL的功能,为什么(???) 缺乏重载的 :(!),我认为“这是一个缺乏”,但@CraigRinger,@Catcall和PostgreSQL的团队同意关于“PG历史悠久的理由”。
PS:关于四舍五入的另一点是准确 ,检查@ IanKenney的答案 。
重载铸造策略
您可以超载与ROUND函数,
CREATE FUNCTION ROUND(float,int) RETURNS NUMERIC AS $$
SELECT ROUND($1::numeric,$2);
$$ language SQL IMMUTABLE;
现在,您的指令将正常工作,尝试(函数创建后)
SELECT round(1/3.,4); -- 0.3333 numeric
但它返回一个数字类型......为了保持第一黎民,使用过载,是提供了一个TEXT参数时,我们可以返回一个float类型,
CREATE FUNCTION ROUND(float, text, int DEFAULT 0)
RETURNS FLOAT AS $$
SELECT CASE WHEN $2='dec'
THEN ROUND($1::numeric,$3)::float
-- ... WHEN $2='hex' THEN ... WHEN $2='bin' THEN... complete!
ELSE 'NaN'::float -- like an error message
END;
$$ language SQL IMMUTABLE;
尝试
SELECT round(1/3.,'dec',4); -- 0.3333 float!
SELECT round(2.8+1/3.,'dec',1); -- 3.1 float!
SELECT round(2.8+1/3.,'dec'::text); -- need to cast string? pg bug
PS:检查\df round
超载后,会显示类似,
Schema | Name | Result data type | Argument data types
------------+-------+------------------+----------------------------
myschema | round | double precision | double precision, text, int
myschema | round | numeric | double precision, int
pg_catalog | round | double precision | double precision
pg_catalog | round | numeric | numeric
pg_catalog | round | numeric | numeric, int
该pg_catalog
功能是默认的,看到的内置的数学函数手册 。
试试这个:
SELECT to_char (2/3::float, 'FM999999990.00');
-- RESULT: 0.67
或者干脆:
SELECT round (2/3::DECIMAL, 2)::TEXT
-- RESULT: 0.67
据Bryan的回应,你可以做到这一点,以限制在查询小数。 我从千米/小时转换成米/秒,并在dygraphs显示,但是当我在dygraphs做到了它看起来怪异。 在查询中做计算的时候,而不是看起来不错。 这是PostgreSQL的9.5.1。
select date,(wind_speed/3.6)::numeric(7,1) from readings;
错误:函数ROUND(双精度整数)不存在
解决方法 :您需要将AddType投那么它会工作
例如: round(extract(second from job_end_time_t)::integer,0)