Postgresql 中文操作指南

67.2. Behavior of B-Tree Operator Classes #

如图所示,btree 运算符类必须提供五个比较运算符 <=>=>。有人可能认为 <> 也应该是运算符类的一部分,但事实并非如此,因为在索引搜索中使用 <> WHERE 子句几乎毫无用处。(出于某些目的,计划程序将 <> 视为与 btree 运算符类相关;但它找到运算符是通过 = 运算符的否定链接,而不是通过 pg_amop。)

当多种数据类型共享近乎相同排序语义时,它们的运算符类可以组合到一个运算符族中。这样做是有利的,因为它允许规划器推断跨类型比较。族中的每个运算符类都应该包含针对其输入数据类型的单类型运算符(和关联的支持函数),而跨类型比较运算符和支持函数则在族中是“松散”的。建议在族中包括一组完整的跨类型运算符,从而确保规划器可以表示从传递性推论出的任何比较条件。

btree 运算符族必须满足一些基本假设:

其他三个运算符根据 =< 以明显的方式定义,并且必须与它们一致。

对于支持多种数据类型的运算符族,当 ABC 从族中的任何数据类型获取时,必须满足上述定律。传递定律最难确保,因为在跨类型情况下,它们表示两个或三个不同运算符行为一致的声明。例如,将 float8numeric 放入同一个运算符族中是行不通的,至少不会使用 numeric 值转换为 float8 以与 float8 进行比较的当前语义。由于 float8 的精度有限,这意味着不同的 numeric 值将与相同的 float8 值相比较,因此传递定律将失败。

对于多数据类型族而言,另一个要求是,包括在运算符族中的数据类型之间定义的任何隐含或二进制强制转换都不得更改关联的排序顺序。

很明显,btree 索引为何需要这些定律在单一数据类型内成立:如果没有它们,将无法对其键进行排序。此外,使用不同数据类型的比较键进行索引搜索要求比较在两种数据类型之间合理地进行。族中扩展到三个或更多数据类型并不是 btree 索引机制本身严格要求的,但是规划器依赖它们进行优化。