2009-07-09 61 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?