- x86_64-pc-linux-gnu上的PostgreSQL 9.6.2,由gcc(GCC)4.4.7 20120313(Red Hat 4.4.7-17)编译,64位。
- 从官方存储库安装。
- postgresql.conf中没有任何变化。
- CentOS 6.8版。
- 用户:postgres。
- BigSQL使用的pgAdmin3 LTS。
- 没有任何异常登录服务器。
我有很多疑问。
在这种情况下,我需要比较具有整数值的字符变化数据类型(可能是表字段)。
- 结果为真或假
select '10' = 10;
select '10' = '10';
select '10'::character varying = '10'::character varying;
select '10'::character varying = 'foo bar';
select '10'::character varying = 'foo bar'::character varying;
select 'foo bar' = 'foo bar';
select '10'::character varying = '10';
- 结果是"运算符不存在:字符变化=整数"
select '10'::character varying = 10;
所以我为比较字符变化和整数创建自定义运算符。
第1步:创建简单的功能
CREATE OR REPLACE FUNCTION public.is_equal_char_int(character varying, integer) RETURNS boolean AS
$BODY$
BEGIN
IF $1 = $2::character varying THEN
RETURN TRUE;
ELSE
RETURN FALSE;
END IF;
End;
$BODY$
LANGUAGE plpgsql VOLATILE COST 100;
第2步:创建新的运算符
CREATE OPERATOR public.=(
PROCEDURE = is_equal_char_int,
LEFTARG = character varying,
RIGHTARG = integer);
所以我解决了我的问题和
select '10'::character varying = 10;
返回真实值。
新问题是: 当我比较字符变化值与未知数据类型值时,postgresql 使用我的自定义运算符。
select '10'::character varying = 'foo bar';
结果是:
整数的输入语法无效:" foo bar"
select pg_typeof('foo bar');
返回未知数据类型。
和下一步我创建了用于比较字符变化和未知数据类型的新运算符。
第1步:
CREATE OR REPLACE FUNCTION public.is_equal_char_unknown(character varying, unknown)
RETURNS boolean AS
$BODY$
BEGIN
IF $1 = $2::character varying THEN
RETURN TRUE;
ELSE
RETURN FALSE;
END IF;
End;
$BODY$
LANGUAGE plpgsql VOLATILE COST 100;
第2步:
CREATE OPERATOR public.=(
PROCEDURE = is_equal_char_unknown,
LEFTARG = character varying,
RIGHTARG = unknown);
当我跑
时select '10'::character varying = 'foo bar';
我给
错误:运算符不唯一:字符变化=未知。
所以我在一个洞里。
答案 0 :(得分:1)
要了解PostgreSQL中运算符的类型解析方式,请阅读文档中的operator type resolution rules。
在您的特殊情况下,在步骤3.a之后仍保留以下操作符:
您的自定义运算符(character varying = integer
)。
character = character
(从character varying
隐式转换为character
)。
name = name
(从character varying
隐式转换为name
)。
text = text
(从character varying
隐式转换为text
)。
规则3.c然后选择您的运算符,因为它是唯一具有精确类型匹配的运算符。如果没有您的运算符,则步骤3.d会选择text = text
,因为text
是字符串类别中唯一的首选类型。
您目前正在做的是发现为什么某些运算符在PostgreSQL中不定义,即为新类型组合定义新的比较运算符会导致导致错误的歧义,因为PostgreSQL无法确定运营商使用。
问题的核心是PostgreSQL 重载运算符的能力,即拥有多个具有相同名称的运算符。然而,这是一个很好的功能,演员和操作员系统经过精心平衡,使体验尽可能好。 unknown
类型也是该系统的一部分。
换句话说,PostgreSQL试图猜测你的意思,但这并不总是可行的。如果你想比较(不是unknown
)字符串和数字,你想要什么?它们应该作为数字还是字符串进行比较? '010'
是否应与10
相同? PostgreSQL并不知道你的意思和放弃。