Re: psql vs perl prepared inserts - Mailing list pgsql-general

From Daniel Verite
Subject Re: psql vs perl prepared inserts
Date
Msg-id 20050413165239.6368792@uruguay
Whole thread Raw
In response to Re: psql vs perl prepared inserts  (Neil Conway <neilc@samurai.com>)
List pgsql-general
    Neil Conway wrote:

> For an INSERT query without any sub-selects
> that is not rewritten by any rules, the cost to parse, rewrite and plan
> the statement is trivial. So I wouldn't expect prepared statements to be
> a big win -- you would gain a lot more from batching multiple inserts
> into a single transaction, and more still from using COPY.

FWIW, when testing pgstream [1] I typically see a 50% increase in execution
speed when switching to prepared statements in such a scenario.
I'm attaching a small test program that inserts 10000 rows into 5 columns, first
without and then with prepared statements, and displays elapsed time.

Example of results:
  elapsed time in loop 0 is 1873 ms (PQexec)
  elapsed time in loop 1 is 1136 ms (PQexecPrepared)
That's with unix domain sockets and a 8.0.1 server.

[1] a thin C++ layer on top of libpq (http://manitou-mail.org/pgstream) that
happens to have a unified API for prepared/non-prepared statements.

--
 Daniel
 PostgreSQL-powered mail user agent and storage: http://www.manitou-mail.org

#include "pgstream.h"
#include <iostream>
#include <stdlib.h>
#include <stdio.h>
#include <sys/time.h>

int main(int argc, char** argv)
{
  const int loops=10000;
  pg_cnx cnx;
  char buf[]="abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ";
  try {
    struct timeval tv1, tv2;
    if (argc < 2) {
      std::cerr << "Usage: " << argv[0] << " connection_string\n";
      exit(1);
    }
    cnx.connect(argv[1]);

    for (int j=0; j<2; j++) {
      cnx.set_option("bind_variables", j>0);
      cnx.set_option("prepare_statements", j>0);
      {
    pg_trans trans(cnx);
    pg_stmt("CREATE TABLE txt1(pk1 int,t1 text,t2 text,"
        "t3 text, t4 text)", cnx);
    gettimeofday(&tv1,NULL);
    pg_stream s1("INSERT INTO txt1(pk1,t1,t2,t3,t4) "
             "VALUES(:i,:p1,:p2,:p3,:p4)", cnx);
    for (int i=0; i<loops; i++) {
      s1 << i << buf << buf << buf << buf;
    }
    gettimeofday(&tv2,NULL);
    pg_stmt("DROP TABLE txt1", cnx);
    trans.commit();
    printf("elapsed time in loop %d is %d ms\n", j,
           (tv2.tv_sec-tv1.tv_sec)*1000+(tv2.tv_usec-tv1.tv_usec)/1000);
      }
    }
  }
  catch(pg_excpt p) {
    std::cerr << p.full_error_txt();
  }
  return 0;
}

pgsql-general by date:

Previous
From: James Robinson
Date:
Subject: Re: Composite type versus Domain constraints.
Next
From: Tom Lane
Date:
Subject: Re: psql vs perl prepared inserts