【发布时间】:2014-12-13 05:10:37
【问题描述】:
我在 PostgreSQL a 和 b 中有 2 个表。
CREATE TABLE a
(
id serial PRIMARY,
name character varying(50) NOT NULL,
);
CREATE TABLE b
(
id serial PRIMARY,
name character varying(50) NOT NULL,
a_id integer,
CONSTRAINT a_id_fk FOREIGN KEY (a_id) REFERENCES a (id)
);
此外,我在b 上有这两个部分索引,以确保b.name 在a 为空时是唯一的,否则(a.name, b.name) 对是唯一的。
CREATE UNIQUE INDEX idx1 ON b (name, a_id) WHERE a_id IS NOT NULL;
CREATE UNIQUE INDEX idx2 ON b (name) WHERE a_id IS NULL;
如果我想查询以下形式的字符串:a.name + ' ' + b.name,这是最有效的方法吗?无论如何我可以创建一个索引来确保(a.name, b.name) 的唯一性并使用它来有效地查询它?
SELECT * FROM b
INNER JOIN a on b.a_id = a.id
WHERE CONCAT(a.name, ' ' , b.name) = 'some string';
我需要精确查找,不需要LIKE / CONTAINS。
【问题讨论】:
-
您的系统中是否需要 (a.name, b.name) 的组合应该是唯一的,或者只是为了提高性能?
-
你不能把“some string”分成“some”和“string”做两个比较吗?
-
我能够创建功能索引
CREATE UNIQUE INDEX idxa ON a (length(name), name) ;(b 相同)。如果(length(a.name) = 4 AND length(b.name) = 4)等被添加到 where 子句中,优化器会使用它,但它无法解开(length(a.name) + length(b.name) = 9)另一种方法是将长度存储在一个额外的列中并使用触发函数来维护它。 -
@Srikanth 唯一性是必需的。 @GordonLinoff 不,复合字符串是外部输入。 @joop 我的理解是功能索引只能在同一张表上工作。
-
这是一个棘手的问题。你能告诉我们更多关于弦的性质吗?
a.name和b.name可以包含空格字符(' ')吗?搜索模式可以包含多个空格字符吗?External input没有说明字符串的外观。a.name和b.name的最小长度是多少?它们中的任何一个都可以是空字符串('')吗?在这种情况下,您还想要b.name前面的空间吗?为什么你使用varchar(50)而不仅仅是varchar或text?
标签: sql postgresql indexing pattern-matching