Skip to content
ClickHouse Docs
ClickHouse DocsClickHouse Docs

Float32 | Float64 | BFloat16 类型

下面列出了 ClickHouse 和 C 中对应的类型:

  • Float32float.
  • Float64double.

ClickHouse 中的 Float 类型有以下别名:

  • Float32FLOAT, REAL, SINGLE.
  • Float64DOUBLE, DOUBLE PRECISION.

创建表时,可以为浮点数指定数值参数 (例如 FLOAT(12)FLOAT(15, 22)DOUBLE(12)DOUBLE(4, 18)) ,但 ClickHouse 会忽略这些参数。

使用浮点数

  • 浮点数运算可能会产生舍入误差。
SELECT 1 - 0.9

  • 计算结果取决于计算方式 (即计算机系统的处理器类型和架构) 。
  • 浮点计算可能会产生无穷大 (Inf) 和“非数” (NaN) 之类的数值。处理计算结果时应考虑到这一点。
  • 从文本中解析浮点数时,结果可能不是机器可表示的最接近值。

NaN 和 Inf

不同于标准 SQL,ClickHouse 支持以下几类浮点数:

  • Inf – 无穷大。
SELECT 0.5 / 0

  • -Inf — 负无穷大。
SELECT -0.5 / 0

  • NaN — 非数值。
SELECT 0 / 0

有关 NaN 排序规则,请参见ORDER BY 子句一节。

集合语义中的非数字值

IEEE 754 标准规定,NaN 在标量比较中满足 NaN = NaN 返回 false。 ClickHouse 对 = 运算符也遵循这一规则。

不过,NaN 并不是某一个单独的值;凡是指数部分全为 1 且 尾数不为 0 的位模式,都属于 NaN。不同的操作以及不同的 CPU 架构都可能产生 具有不同符号位或不同尾数载荷的 NaN 值。例如:

  • 0./0. 会产生一个 NaN,在大多数 x86 平台上其符号位为 1。
  • 字面量 nan 会产生一个符号位为 0 的 NaN
  • PR #98230 之后,AArch64 NEON 路径上的 log 在输入为负时返回的 NaN,其符号位与 glibc 的标量 log 不同。

ClickHouse 中的哈希表会按字节比较键,因此不同的 NaN 位模式会被哈希到 不同的桶中,并在包括 DISTINCTGROUP BYuniqExactcountDistinct 以及基于 Float 键的等值 JOIN 在内的集合语义操作中 被视为不同的值:

SELECT countDistinct(arrayJoin([0./0., nan, log(-1.)]));
-- May return 2 or 3 depending on architecture and build, even though all three inputs are NaN.

这与 IEEE 754 一致 (每个 NaN 都不等于任何其他值,包括它自身) , 但这可能会让人感到意外。如果你需要基于集合语义的操作将所有 NaN 值视为相等, 请在查询中将它们规范化:

-- Replace every NaN with a single canonical NaN value
SELECT countDistinct(if(isNaN(x), CAST('nan' AS Float64), x))
FROM (SELECT arrayJoin([0./0., nan, log(-1.)]) AS x);
-- Returns 1.

-- Or exclude NaN values from the set entirely
SELECT countDistinct(if(isNaN(x), NULL, x))
FROM (SELECT arrayJoin([0./0., nan, log(-1.)]) AS x);
-- Returns 0.

同样的方法也适用于 DISTINCTGROUP BYJOIN 的键。

BFloat16

BFloat16 是一种 16 位浮点数据类型,由 8 位指数、符号位和 7 位尾数组成。 它适用于机器学习和 AI 应用。

ClickHouse 支持在 Float32BFloat16 之间进行转换, 可使用 toFloat32()toBFloat16 函数。

Navigation