2009-07-09 29 views
0

我的应用程序在PostgreSQL中使用临时表。 随着新的,8.4版本我测试其性能比较 到旧的8.2版本,我观察到,临时表 是十个十倍慢!从8.3开始,您是否观察到PostgreSQL TEMP TABLE性能下降?

8.3版本的测试表明它在8.3中也比较慢。我比较了所有 基地的配置,它们是相似的。所有的基地在相同的 服务器上工作。虽然我的应用程序使用JDBC驱动程序我用的Jython 测试它:

import time 
import traceback 
import sys 

from java.sql import DriverManager 
from java.lang import Class 

Class.forName("org.postgresql.Driver") 

def test_bench(db, temp): 
    if temp: 
     temp_str = ' TEMP ' 
     temp_desc = 'temp ' 
    else: 
     temp_str = ' ' 
     temp_desc = 'regular' 
    try: 
     c = db.createStatement() 
     c.execute("CREATE %s TABLE test_table_md_speed(id serial primary key, txt varchar(100))" % temp_str) 
     cnt = '?' 
     try: 
      t0 = time.time() 
      for i in range(1000): 
       c.execute("INSERT INTO test_table_md_speed(txt) VALUES ('ala ma %d kota')" % i) 
      t2 = time.time() 
      rs = c.executeQuery("SELECT COUNT(*) AS ile FROM test_table_md_speed") 
      while (rs.next()): 
       cnt = rs.getString(1) 
      print("%s\ttime: %7.3f [s]\tcnt: %s" % (temp_desc, (t2-t0), cnt)) 
     finally: 
      c.execute("DROP TABLE test_table_md_speed") 
     c.close() 
    except: 
     print("\nthere were errors!") 
     s = traceback.format_exc() 
     sys.stderr.write("%s\n" % (s)) 

def test_db(db_url, usr, passwd): 
    print("\n\n--------------") 
    db = DriverManager.getConnection(db_url, usr, passwd) 
    try: 
     c = db.createStatement() 
     rs = c.executeQuery("SELECT version()") 
     while (rs.next()): 
      print('ver: %s' % (rs.getString(1))) 
     test_bench(db, 0) 
     test_bench(db, 1) 
    finally: 
     db.close() 

test_db('jdbc:postgresql://db-test64:5432/db_stable?stringtype=unspecified', 'postgres', 'postgres') 
test_db('jdbc:postgresql://db-test64:5434/db_stable?stringtype=unspecified', 'postgres', 'postgres') 
test_db('jdbc:postgresql://db-test64:5435/db_stable?stringtype=unspecified', 'postgres', 'postgres') 

我也写了使用ActivePython的类似的测试和ODBC从Win32和该程序显示了同样的结果。 我的结果:

C:\tools\pyscripts\>jython jdbc_pg_bench.py 
-------------- 
ver: PostgreSQL 8.2.12 on x86_64-unknown-linux-gnu, compiled by GCC gcc (GCC) 4.1.2 20061115 (prerelease) (Debian 4.1.1-21) 
regular time: 12.016 [s]  cnt: 1000 
temp time: 1.187 [s]  cnt: 1000 
-------------- 
ver: PostgreSQL 8.3.6 on x86_64-unknown-linux-gnu, compiled by GCC gcc (GCC) 4.1.2 20061115 (prerelease) (Debian 4.1.1-21) 
regular time: 11.922 [s]  cnt: 1000 
temp time: 10.516 [s]  cnt: 1000 
-------------- 
ver: PostgreSQL 8.4.0 on x86_64-unknown-linux-gnu, compiled by GCC gcc (GCC) 4.1.2 20061115 (prerelease) (Debian 4.1.1-21), 64-bit 
regular time: 13.375 [s]  cnt: 1000 
temp time: 13.609 [s]  cnt: 1000 

你观察临时表的速度相同降解8.3和8.4版本? 有关于TEMP表行为变化的任何信息吗?

编辑

我在我的Windows机器上安装的PostgreSQL 8.2和8.4,与10条000插入测试,它似乎8.2快得多用临时表:

ver: PostgreSQL 8.2.11 on i686-pc-mingw32, compiled by GCC gcc.exe (GCC) 3.4.2 (mingw-special) 
regular time: 40.672 [s]  cnt: 10000 
temp time: 14.859 [s]  cnt: 10000 

ver: PostgreSQL 8.4.0, compiled by Visual C++ build 1400, 32-bit 
regular time: 56.860 [s]  cnt: 10000 
temp time: 49.110 [s]  cnt: 10000 

回答

1

我检查 - 但我不能重复你的结果。在我的计算机上,插入临时表的速度与我测试的所有版本类似。这有点奇怪,所以在你的补丁上插入8.2.12比插入常规表快10倍。在我的计算机上插入到临时表的速度比插入到常规表的速度快大约1.5-2倍。

+0

感谢您的测试。我会在其他机器上重复我的测试。 – 2009-07-10 10:09:27

+0

我在我的Windows机器上使用全新安装对其进行了测试,并且当我在查询中添加时,8.4上的常规表和临时表几乎没有区别,而8.2上的临时表更快。 – 2009-07-13 10:18:57

3

8.3引入这种变化:(从commit log on the wiki

2007-06-03 13:05 TGL创建GUC参数temp_tablespaces,允许表空间(S),在其中存储临时表和选择临时文件。这是一个允许将负载分散到多个表空间的列表(每次创建临时对象时都会选择一个随机列表元素)。临时文件不再存储在每个数据库的pgsql_tmp/目录中,而是存储在每个表空间的目录中。

Release notes给信贷“海梅卡萨诺瓦,阿尔伯特塞韦拉,贝恩德Helmle”


有到pgsql-performance列表可能与报告。楼主确定了changing their kernel at the same time was more likely the cause,但是a post from Tom Lane包括:

“所以我怀疑你看到的放缓源于制作 较大数量的8.3目录更新的;”


您的评论是,8.2的配置被复制为8.3 ...默认自动清理设置由截止到改变。也许你的临时表在8.3被抽真空,但不在8.2?