Optimization PostgreSQL查询优化和Postmaster流程的实现

Optimization PostgreSQL查询优化和Postmaster流程的实现,optimization,postgresql,indexing,rdbms,Optimization,Postgresql,Indexing,Rdbms,我目前正在使用一个更大的维基百科转储派生的PostgreSQL数据库;它包含大约40GB的数据。数据库运行在带有Suse Linux Enterprise server 10的HP Proliant ML370 G5服务器上;我通过一个简单的D-Link路由器管理的专用网络从我的笔记本电脑上查询它。我为笔记本电脑和服务器分配了静态DHCP专用IP 无论如何,在我的笔记本电脑上,使用pgAdmin III,我发送了一些SQL命令/查询;其中一些是CREATE INDEX、DROP INDEX、DE

我目前正在使用一个更大的维基百科转储派生的PostgreSQL数据库;它包含大约40GB的数据。数据库运行在带有Suse Linux Enterprise server 10的HP Proliant ML370 G5服务器上;我通过一个简单的D-Link路由器管理的专用网络从我的笔记本电脑上查询它。我为笔记本电脑和服务器分配了静态DHCP专用IP

无论如何,在我的笔记本电脑上,使用pgAdmin III,我发送了一些SQL命令/查询;其中一些是CREATE INDEX、DROP INDEX、DELETE、SELECT等。有时我会发送一个命令,比如CREATE INDEX,它会返回,告诉我查询执行得很好,等等。但是,分配给这样一个命令的邮局主管进程似乎仍在服务器上休眠。现在,我并不真的介意这一点,因为我对自己说,PostgreSQL维护着一个随时准备处理查询的邮局管理员池。然而,如果这个过程占用了6GB的it 9.4GB分配RAM,我会担心,而且它目前正在这样做。现在可能这是一个数据缓存,保存在[共享]内存中,以防另一个查询碰巧需要使用相同的数据,但我不知道

另一件事困扰着我

我有两张桌子。一是页面表;我在它的page\u id列上有一个索引。另一个是pagelinks表,它的pl_from列在page.page_id列中不引用任何内容或引用变量;与page_id列不同,pl_from还没有索引。为了让您了解表的规模以及我找到可行解决方案的必要性,在我删除了不需要的行之后,page table有1340万行,而pagelinks表有2.93亿行

我需要执行以下命令来清除pagelinks表中的一些无用行:

DELETE FROM pagelinks USING page WHERE pl_from NOT IN (page_id);
因此,基本上,我希望将pagelinks表中不在pagelinks表中的页面中的所有链接删除。即使在禁用嵌套循环和/或顺序扫描后,查询优化器始终为我提供以下解决方案:

Nested Loop  (cost=494640.60..112115531252189.59 rows=3953377028232000 width=6)
  Join Filter: ("outer".pl_from <> "inner".page_id)"
  ->  Seq Scan on pagelinks  (cost=0.00..5889791.00 rows=293392800 width=17)
  ->  Materialize  (cost=494640.60..708341.51 rows=13474691 width=11)
        ->  Seq Scan on page  (cost=0.00..402211.91 rows=13474691 width=11)

这项任务似乎需要数周以上的时间才能完成;显然,这是不可接受的。在我看来,我更希望它使用page_id索引来完成它的工作……但它是一个顽固的优化器,我可能错了

关于你的第二个问题;您可以尝试使用CREATETABLEAS语句创建一个新表,其中只包含所需的记录;如果新表足够小,它可能会更快,但也可能没有帮助。

事实上,我决定创建一个临时表来加速查询执行:

CREATE TABLE temp_to_delete AS(
    (SELECT DISTINCT pl_from FROM pagelinks) 
        EXCEPT 
    (SELECT page_id FROM page));
DELETE FROM pagelinks USING temp_to_delete 
    WHERE pagelinks.pl_from IN (temp_to_delete.pl_from);
令人惊讶的是,这个查询在大约4小时内完成,而最初的查询在我决定终止它之前已经保持了大约14小时的活动状态。更具体地说,删除返回:

Query returned successfully: 31340904 rows affected, 4415166 ms execution time.
至于我问题的第一部分,似乎邮局主管程序确实在缓存中保存了一些信息;当另一个查询需要不在缓存中的信息和一些内存RAM时,缓存将清空。而邮递员实际上只是一个“流程库”

我也意识到gnome系统监视器是一个神话,因为它提供的信息不完整,在信息价值上毫无价值。这主要是由于这个应用程序,我最近一直很困惑;例如,它不考虑其他用户的内存使用,如PASGRESs用户!甚至告诉我,我还有12GB的内存,但这是不真实的。因此,我尝试了几个系统监视器,因为我想知道postgreSQL是如何使用它的资源的,而xosview似乎确实是一个有效的工具


希望这有帮助

只要与客户端的连接处于打开状态,您的postmaster进程就会一直保持在那里。 pgadmin是否关闭连接?我不知道

使用的内存可能是共享的,请检查配置设置

现在是查询。对于这样的大型维护操作,可以随意将work_mem设置为几GB之类的大值。你看起来有很多内存,所以使用它

将work_mem设置为“4GB”; 解释从页面删除链接,其中pl_FROM不在选择页面id FROM页面中

它应该依次扫描页面、散列页面和顺序扫描页面链接,查看散列以检查页面ID。它应该相当快,比4小时快得多!但是你需要一个大的工作记忆来做散列

但是,由于删除了表的很大一部分,这样做可能会更快:

创建表pagelinks2作为从pagelinks中选择a.*连接a.pl_FROM=b.page_id上的页面b

您可以使用简单的联接,而不是IN


您还可以在此查询中添加一个ORDER BY,您的新表将很好地在磁盘上排序,以便以后进行最佳访问。

实际上,这是我正在尝试的,这似乎是我的最佳选择。我会张贴的结果,如果它的工作。谢谢!