Performance postgresql:垂直分区没有带来性能改进
我努力用垂直分区优化表的性能。以下Select语句应在postgre imho中进行优化:Performance postgresql:垂直分区没有带来性能改进,performance,postgresql,query-optimization,vertical-partitioning,Performance,Postgresql,Query Optimization,Vertical Partitioning,我努力用垂直分区优化表的性能。以下Select语句应在postgre imho中进行优化: SELECT "ProductView".name, "ProductView".price, "ProductView".pid FROM "DefaultSchema"."ProductView"; 我的模式如下所示: tables: ProductA(**pid**, name, price) ProductB(**pid**, desc) view: Product(**
SELECT
"ProductView".name,
"ProductView".price,
"ProductView".pid
FROM
"DefaultSchema"."ProductView";
我的模式如下所示:
tables:
ProductA(**pid**, name, price)
ProductB(**pid**, desc)
view:
Product(**pid**,name, price, desc)
SQL:
CREATE TABLE "DefaultSchema"."ProductA"
(
pid integer NOT NULL,
price integer,
name text,
CONSTRAINT pk_pa PRIMARY KEY (pid)
)
CREATE TABLE "DefaultSchema"."ProductB"
(
pid integer NOT NULL,
"desc" text,
CONSTRAINT "PK_PB" PRIMARY KEY (pid),
CONSTRAINT "FK_PID" FOREIGN KEY (pid)
REFERENCES "DefaultSchema"."ProductA" (pid) MATCH SIMPLE
ON UPDATE CASCADE ON DELETE CASCADE
)
CREATE OR REPLACE VIEW "DefaultSchema"."ProductView" AS
SELECT p1.pid,
p1.price,
p1.name,
p2."desc"
FROM "DefaultSchema"."ProductA" p1
JOIN "DefaultSchema"."ProductB" p2 ON p1.pid = p2.pid;
因此,您可能会认识到,对于select查询,我并不真正需要ProductB。然而,正如您在这里看到的,它在执行过程中被连接
"Hash Join (cost=36.10..74.61 rows=1160 width=40) (actual time=0.090..0.105 rows=7 loops=1)"
" Hash Cond: (p2.pid = p1.pid)"
" -> Seq Scan on "ProductB" p2 (cost=0.00..22.30 rows=1230 width=4) (actual time=0.022..0.027 rows=7 loops=1)"
" -> Hash (cost=21.60..21.60 rows=1160 width=40) (actual time=0.030..0.030 rows=7 loops=1)"
" Buckets: 1024 Batches: 1 Memory Usage: 1kB"
" -> Seq Scan on "ProductA" p1 (cost=0.00..21.60 rows=1160 width=40) (actual time=0.010..0.017 rows=7 loops=1)"
"Total runtime: 0.299 ms"
我的问题是如何强制postgre只扫描ProductA?我是否需要一个额外的约束,编辑配置文件,还是不可能通过postgre中的垂直分区获得性能优势?事先多谢 PostgreSQL的查询计划器尚未对内部联接执行联接删除操作 您可以单独查询ProductA,也可以重写视图以使用左外部联接。PostgreSQL 9.0+对左侧外部联接执行联接删除
CREATE OR REPLACE VIEW "DefaultSchema"."ProductView" AS
SELECT p1.pid,
p1.price,
p1.name,
p2."desc"
FROM "DefaultSchema"."ProductA" p1
LEFT JOIN "DefaultSchema"."ProductB" p2 ON p1.pid = p2.pid;
explain analyze
SELECT "ProductView".name, "ProductView".price, "ProductView".pid
FROM "ProductView";
在每个应用程序中,重写使用左外部联接并不安全,但我认为对于您的特定问题是安全的 总运行时间:0.299毫秒,应该快多少?这几乎是零,很难改进。1毫秒很快,但是0.299毫秒,真的很快,比我们大多数人眨眼的速度都快…总时间是不相关的,因为在这个测试场景中,我只有7条记录。有趣的是DBMS如何以语义方式优化查询。如果我想象我有一百万条记录,如果我只扫描一张表,或者扫描两张表并加入它们,那将是一个巨大的不同。非常感谢迈克,你绝对说到点子上了!现在有点道理了。我认为不接触表就不可能优化内部联接。从逻辑的角度来看,我不能确定内部联接的结果,因此无法对其进行优化。 QUERY PLAN -- Seq Scan on "ProductA" p1 (cost=0.00..20.00 rows=1000 width=41) (actual time=0.008..0.225 rows=1000 loops=1)