Collation 差异导致 KingbaseES 与 Oracle 查询结果不同

问题引入

前端提了个问题,说是KingbaseES 返回的结果与 Oracle 返回的结果不一样。具体问题如下:

oracle 执行结果:oracle 有结果返回。

SQL> create table t3(id varchar(9));

Table created.

SQL>insert into t3 values('abcd');

1 row created.

SQL>select * from t3 where  id<='abc~';

ID
---------
abcd

 

KingbaseES 执行结果:无结果返回

test=# create table t3(id varchar(9));
CREATE TABLE
test=# insert into t3 values('abcd');
INSERT 0 1
test=# select * from t3 where  id<='abc~';
 id
----
(0 rows)

 

问题分析

查看数据库排序规则

test=# \l
                               List of databases
   Name    | Owner  | Encoding |   Collate   |    Ctype    | Access privileges
-----------+--------+----------+-------------+-------------+-------------------
 security  | system | UTF8     | en_US.UTF-8 | en_US.UTF-8 |
 template0 | system | UTF8     | en_US.UTF-8 | en_US.UTF-8 | =c/system        +
           |        |          |             |             | system=CTc/system
 template1 | system | UTF8     | en_US.UTF-8 | en_US.UTF-8 | =c/system        +
           |        |          |             |             | system=CTc/system
 test      | system | UTF8     | en_US.UTF-8 | en_US.UTF-8 |

尝试用 collate "c" 验证

test=# select * from t3 where  id<='abc~' collate "C";
  id
------
 abcd
(1 row)

 

问题结论

1、oracle 默认 collation binary (可以看 dba_users.DEFAULT_COLLATION = 'USING_NLS_COMP' ,也就是参照nls_database_parameters.NLS_SORT 的值),二进制的排序可能并不适用于语言的规则。

2、KingbaseES 默认使用语言的规则进行排序,如果要使用二进制排序,可以使用 “C” or "POSIX"

 

最后再看个差异的例子:

oracle 二进制排序:

SQL> select * from t3 order by 1;

ID
---------
MacDonald
MacIntosh
Macdonald
Macintosh

 

KingbaseES en_US.UTF-8 排序

test=# select * from t3 order by 1;
    id
-----------
 Macdonald
 MacDonald
 Macintosh
 MacIntosh


test=# select * from t3 order by id collate "C";
    id
-----------
 MacDonald
 MacIntosh
 Macdonald
 Macintosh

 

posted @ 2023-02-28 17:45  KINGBASE研究院  阅读(65)  评论(0编辑  收藏  举报