On Mon, 26 Feb 2001, J. T. Vermeulen wrote:
> Suggest the following fixes for a future version. These include some minor
> changes of interface (ints changed to bools) that should be compatible at the
> source level but incompatible at the linking level, so those may have to be
> skipped or deferred to some more convenient time.
>
> Other changes: fixed possible portability problem for weird platforms (using
> memset() to clear pointers); fixed minor memory leak in PrintTuples(), and
> marked PrintTuples() / DisplayTuples() as obsolescent; changed dubious
> parameter names "string" to "str".
Oh, and made constructor 'explicit' for greater safety.
Here's an updated version of the same patch. Added changes:- made lots of member functions 'const'- documented
GetIsNull()-updated documentation for interface changes
Diffs follow:
--- postgresql-7.0.3/src/interfaces/libpq++/pgdatabase.h Sun Apr 23 00:39:15 2000
+++ postgresql-7.0.3-jtv/src/interfaces/libpq++/pgdatabase.h Mon Feb 26 15:06:59 2001
@@ -37,35 +37,37 @@class PgDatabase : public PgConnection {public: // connect to the database with conninfo
- PgDatabase(const char* conninfo) : PgConnection(conninfo) {}
+ explicit PgDatabase(const char conninfo[]) : PgConnection(conninfo) {} ~PgDatabase() {} // close
connectionand clean up // query result access
- int Tuples();
- int CmdTuples();
+ int Tuples() const;
+ int CmdTuples() const; int Fields();
- const char* FieldName(int field_num);
- int FieldNum(const char* field_name);
- Oid FieldType(int field_num);
- Oid FieldType(const char* field_name);
- short FieldSize(int field_num);
- short FieldSize(const char* field_name);
- const char* GetValue(int tup_num, int field_num);
- const char* GetValue(int tup_num, const char* field_name);
- int GetIsNull(int tup_num, int field_num);
- int GetIsNull(int tup_num, const char* field_name);
- int GetLength(int tup_num, int field_num);
- int GetLength(int tup_num, const char* field_name);
- void DisplayTuples(FILE *out = 0, int fillAlign = 1,
- const char* fieldSep = "|",int printHeader = 1, int quiet = 0) ;
- void PrintTuples(FILE *out = 0, int printAttName = 1,
- int terseOutput = 0, int width = 0) ;
+ const char* FieldName(int field_num) const;
+ int FieldNum(const char* field_name) const;
+ Oid FieldType(int field_num) const;
+ Oid FieldType(const char* field_name) const;
+ short FieldSize(int field_num) const;
+ short FieldSize(const char* field_name) const;
+ const char* GetValue(int tup_num, int field_num) const;
+ const char* GetValue(int tup_num, const char* field_name) const;
+ bool GetIsNull(int tup_num, int field_num) const;
+ bool GetIsNull(int tup_num, const char* field_name) const;
+ int GetLength(int tup_num, int field_num) const;
+ int GetLength(int tup_num, const char* field_name) const;
+
+ // OBSOLESCENT (use PQprint()):
+ void DisplayTuples(FILE *out=0, bool fillAlign=true,
+ const char* fieldSep="|", bool printHeader=true, bool quiet=false) const;
+ void PrintTuples(FILE *out=0, bool printAttName=true,
+ bool terseOutput=false, bool fillAlign=false) const; // copy command related access
- int GetLine(char* string, int length);
- void PutLine(const char* string);
- const char* OidStatus();
+ int GetLine(char str[], int length);
+ void PutLine(const char str[]);
+ const char* OidStatus() const; int EndCopy(); protected:
--- postgresql-7.0.3/src/interfaces/libpq++/pgdatabase.cc Sat Jan 29 17:58:52 2000
+++ postgresql-7.0.3-jtv/src/interfaces/libpq++/pgdatabase.cc Mon Feb 26 15:09:59 2001
@@ -18,57 +18,57 @@#include "pgdatabase.h"
-void PgDatabase::DisplayTuples(FILE *out, int fillAlign,
- const char* fieldSep, int printHeader,
- int /* quiet */)
+// OBSOLESCENT (uses PQprint(), which is no longer being maintained)
+void PgDatabase::DisplayTuples(FILE *out,
+ bool fillAlign,
+ const char* fieldSep,
+ bool printHeader,
+ bool /* quiet */) const{ PQprintOpt po;
- memset(&po,0,sizeof(po));
-
- po.align = fillAlign;
- po.fieldSep = (char *)fieldSep; po.header = printHeader;
+ po.align = fillAlign;
+ po.standard = po.html3 = po.expanded = po.pager = 0;
+ po.fieldSep = const_cast<char *>(fieldSep);
+ po.tableOpt = po.caption = 0;
+ po.fieldName = 0; PQprint(out,pgResult,&po);}
-
-void PgDatabase::PrintTuples(FILE *out, int printAttName, int terseOutput,
- int width)
+// OBSOLESCENT (uses PQprint(), which is no longer being maintained)
+void PgDatabase::PrintTuples(FILE *out,
+ bool printAttName,
+ bool terseOutput,
+ bool fillAlign) const{ PQprintOpt po;
- memset(&po,0,sizeof(po));
-
- po.align = width;
-
- if(terseOutput) po.fieldSep = strdup("|");
- else po.fieldSep = "";
- po.header = printAttName;
+ po.align = fillAlign;
+ po.standard = po.html3 = po.expanded = po.pager = 0;
+ po.tableOpt = po.caption = 0;
+ po.fieldSep = const_cast<char *>(terseOutput ? "" : "|");
+ po.fieldName = 0; PQprint(out,pgResult,&po);}
-int PgDatabase::Tuples()
+int PgDatabase::Tuples() const{ return PQntuples(pgResult); }
-int PgDatabase::CmdTuples()
+int PgDatabase::CmdTuples() const{
-char *a;
-
- a = (char *)PQcmdTuples(pgResult);
- if(!a[0]) return -1;
-
-return atoi(a);
+const char *a = PQcmdTuples(pgResult);
+return a[0] ? atoi(a) : -1;}
@@ -78,91 +78,91 @@}
-const char* PgDatabase::FieldName(int field_num)
+const char* PgDatabase::FieldName(int field_num) const{ return PQfname(pgResult, field_num); }
-int PgDatabase::FieldNum(const char* field_name)
+int PgDatabase::FieldNum(const char* field_name) const{ return PQfnumber(pgResult, field_name); }
-Oid PgDatabase::FieldType(int field_num)
+Oid PgDatabase::FieldType(int field_num) const{ return PQftype(pgResult, field_num); }
-Oid PgDatabase::FieldType(const char* field_name)
+Oid PgDatabase::FieldType(const char* field_name) const{ return PQftype(pgResult, FieldNum(field_name)); }
-short PgDatabase::FieldSize(int field_num)
+short PgDatabase::FieldSize(int field_num) const{ return PQfsize(pgResult, field_num); }
-short PgDatabase::FieldSize(const char* field_name)
+short PgDatabase::FieldSize(const char* field_name) const{ return PQfsize(pgResult, FieldNum(field_name)); }
-const char* PgDatabase::GetValue(int tup_num, int field_num)
+const char* PgDatabase::GetValue(int tup_num, int field_num) const{ return PQgetvalue(pgResult, tup_num, field_num);
}
-const char* PgDatabase::GetValue(int tup_num, const char* field_name)
+const char* PgDatabase::GetValue(int tup_num, const char* field_name) const{ return PQgetvalue(pgResult, tup_num,
FieldNum(field_name));}
-int PgDatabase::GetIsNull(int tup_num, int field_num)
+bool PgDatabase::GetIsNull(int tup_num, int field_num) const{ return PQgetisnull(pgResult, tup_num, field_num); }
-int PgDatabase::GetIsNull(int tup_num, const char* field_name)
+bool PgDatabase::GetIsNull(int tup_num, const char* field_name) const{ return PQgetisnull(pgResult, tup_num,
FieldNum(field_name));}
-int PgDatabase::GetLength(int tup_num, int field_num)
+int PgDatabase::GetLength(int tup_num, int field_num) const{ return PQgetlength(pgResult, tup_num, field_num); }
-int PgDatabase::GetLength(int tup_num, const char* field_name)
+int PgDatabase::GetLength(int tup_num, const char* field_name) const{ return PQgetlength(pgResult, tup_num,
FieldNum(field_name));}
-int PgDatabase::GetLine(char* string, int length)
+int PgDatabase::GetLine(char str[], int length){
-return PQgetline(pgConn, string, length);
+return PQgetline(pgConn, str, length); }
-void PgDatabase::PutLine(const char* string)
+void PgDatabase::PutLine(const char str[]){
-PQputline(pgConn, string);
+PQputline(pgConn, str); }
-const char* PgDatabase::OidStatus()
+const char* PgDatabase::OidStatus() const{ return PQoidStatus(pgResult); }
--- postgresql-7.0.3/doc/src/sgml/libpq++.sgml Tue May 2 22:01:51 2000
+++ postgresql-7.0.3-jtv/doc/src/sgml/libpq++.sgml Mon Feb 26 15:17:14 2001
@@ -354,7 +354,7 @@ <function>Tuples</function> Returns the number of tuples (instances) in the query
result. <synopsis>
- int PgDatabase::Tuples()
+ int PgDatabase::Tuples() const </synopsis> </para> </listitem>
@@ -364,7 +364,7 @@ Returns the number of rows affected after an INSERT, UPDATE or DELETE.
Ifthe command was anything else, it returns -1. <synopsis>
- int PgDatabase::CmdTuples()
+ int PgDatabase::CmdTuples() const </synopsis> </para> </listitem>
@@ -383,7 +383,7 @@ Returns the field (attribute) name associated with the given field index. Field
indicesstart at 0. <synopsis>
- const char *PgDatabase::FieldName(int field_num)
+ const char *PgDatabase::FieldName(int field_num) const </synopsis> </para> </listitem>
@@ -393,7 +393,7 @@ PQfnumber Returns the field (attribute) index associated with the given field name.
<synopsis>
- int PgDatabase::FieldNum(const char* field_name)
+ int PgDatabase::FieldNum(const char* field_name) const </synopsis> -1 is returned if the given name
doesnot match any field. </para>
@@ -405,7 +405,7 @@ integer returned is an internal coding of the type. Field indices start at 0.
<synopsis>
- Oid PgDatabase::FieldType(int field_num)
+ Oid PgDatabase::FieldType(int field_num) const </synopsis> </para> </listitem>
@@ -416,7 +416,7 @@ integer returned is an internal coding of the type. Field indices start at 0.
<synopsis>
- Oid PgDatabase::FieldType(const char* field_name)
+ Oid PgDatabase::FieldType(const char* field_name) const </synopsis> </para> </listitem>
@@ -426,7 +426,7 @@ Returns the size in bytes of the field associated with the given field index. Field
indicesstart at 0. <synopsis>
- short PgDatabase::FieldSize(int field_num)
+ short PgDatabase::FieldSize(int field_num) const </synopsis> Returns the space allocated for this
fieldin a database tuple given the field number. In other words the size of the server's binary
@@ -440,7 +440,7 @@ Returns the size in bytes of the field associated with the given field index. Field
indicesstart at 0. <synopsis>
- short PgDatabase::FieldSize(const char *field_name)
+ short PgDatabase::FieldSize(const char *field_name) const </synopsis> Returns the space allocated for
thisfield in a database tuple given the field name. In other words the size of the server's binary
@@ -454,7 +454,7 @@ Returns a single field (attribute) value of one tuple of a PGresult. Tuple and field
indicesstart at 0. <synopsis>
- const char *PgDatabase::GetValue(int tup_num, int field_num)
+ const char *PgDatabase::GetValue(int tup_num, int field_num) const </synopsis> For most queries, the
valuereturned by GetValue is a null-terminated ASCII string representation of the attribute value. But if
BinaryTuples()
@@ -474,7 +474,7 @@ Returns a single field (attribute) value of one tuple of a PGresult. Tuple and field
indicesstart at 0. <synopsis>
- const char *PgDatabase::GetValue(int tup_num, const char *field_name)
+ const char *PgDatabase::GetValue(int tup_num, const char *field_name) const </synopsis> For most
queries,the value returned by GetValue is a null-terminated ASCII string representation of the attribute value.
Butif BinaryTuples()
@@ -490,11 +490,33 @@ </listitem> <listitem> <para>
+ <function>GetIsNull</function>
+ Returns whether a field has the null value.
+ <synopsis>
+ bool GetIsNull(int tup_num, int field_num) const
+ </synopsis>
+ Note that GetValue will return the empty string for null fields, not
+ the NULL pointer.
+ </para>
+ </listitem>
+ <listitem>
+ <para>
+ <function>GetIsNull</function>
+ Returns whether a field has the null value.
+ <synopsis>
+ bool GetIsNull(int tup_num, const char* field_name) const
+ </synopsis>
+ Note that GetValue will return the empty string for null fields, not
+ the NULL pointer.
+ </para>
+ </listitem>
+ <listitem>
+ <para> <function>GetLength</function> Returns the length of a field (attribute) in bytes. Tuple and
field indices start at 0. <synopsis>
- int PgDatabase::GetLength(int tup_num, int field_num)
+ int PgDatabase::GetLength(int tup_num, int field_num) const </synopsis> This is the actual data length
forthe particular data value, that is the size of the object pointed to by GetValue. Note that for
@@ -508,7 +530,7 @@ Returns the length of a field (attribute) in bytes. Tuple and field indices start at
0. <synopsis>
- int PgDatabase::GetLength(int tup_num, const char* field_name)
+ int PgDatabase::GetLength(int tup_num, const char* field_name) const </synopsis> This is the actual
datalength for the particular data value, that is the size of the object pointed to by GetValue. Note that for
@@ -522,8 +544,8 @@ Prints out all the tuples and, optionally, the attribute names to the specified output
stream. <synopsis>
- void PgDatabase::DisplayTuples(FILE *out = 0, int fillAlign = 1,
- const char* fieldSep = "|",int printHeader = 1, int quiet = 0)
+ void PgDatabase::DisplayTuples(FILE *out = 0, bool fillAlign = true,
+ const char* fieldSep = "|",bool printHeader = true, bool quiet = false) const </synopsis> </para>
</listitem>
@@ -533,8 +555,8 @@ Prints out all the tuples and, optionally, the attribute names to the specified output
stream. <synopsis>
- void PgDatabase::PrintTuples(FILE *out = 0, int printAttName = 1,
- int terseOutput = 0, int width = 0)
+ void PgDatabase::PrintTuples(FILE *out = 0, bool printAttName = true,
+ bool terseOutput = false, bool fillAlign = false) const </synopsis> </para> </listitem>
@@ -558,7 +580,7 @@ <para> <function>OidStatus</function> <synopsis>
- const char *PgDatabase::OidStatus()
+ const char *PgDatabase::OidStatus() const </synopsis> </para> </listitem>
@@ -612,8 +634,8 @@ to see if any notification data is currently available from the backend.
<function>PgDatabase::Notifies</function> returns the notification from a list of unhandled notifications from the
- backend. The function eturns NULL if there is no pending notifications from the
- backend.
+ backend. The function returns NULL if there is no pending notifications
+ from the backend. <function>PgDatabase::Notifies</function> behaves like the popping of a stack. Once a
notificationis returned from <function>PgDatabase::Notifies</function>,
Jeroen