00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019 #ifdef PQXX_HAVE_IOS
00020 #include <ios>
00021 #endif
00022
00023 #include <stdexcept>
00024
00025 #include "pqxx/util"
00026
00027
00028
00029
00030
00031
00032 namespace pqxx
00033 {
00035
00042 class PQXX_LIBEXPORT result : private internal::PQAlloc<internal::pq::PGresult>
00043 {
00044 typedef internal::PQAlloc<internal::pq::PGresult> super;
00045 public:
00046 class const_iterator;
00047 class const_fielditerator;
00048 class const_reverse_fielditerator;
00049 class tuple;
00050 class field;
00051 typedef unsigned long size_type;
00052 typedef signed long difference_type;
00053 typedef tuple reference;
00054 typedef const_iterator pointer;
00055
00057
00068 class PQXX_LIBEXPORT tuple
00069 {
00070 public:
00071 typedef unsigned int size_type;
00072 typedef signed int difference_type;
00073 typedef const_fielditerator const_iterator;
00074 typedef field reference;
00075 typedef const_fielditerator pointer;
00076 typedef const_reverse_fielditerator const_reverse_iterator;
00077
00078 tuple(const result *r, result::size_type i) throw () :
00079 m_Home(r), m_Index(i) {}
00080 ~tuple() throw () {}
00081
00082 bool operator==(const tuple &) const throw ();
00083 bool operator!=(const tuple &rhs) const throw ()
00084 { return !operator==(rhs); }
00085
00086 const_iterator begin() const throw ()
00087 { return const_iterator(*this, 0); }
00088 const_iterator end() const throw ()
00089 { return const_iterator(*this, size()); }
00090
00091 reference front() const throw () { return field(*this, 0); }
00092 reference back() const throw () { return field(*this, size()-1); }
00093
00094 const_reverse_fielditerator rbegin() const;
00095 const_reverse_fielditerator rend() const;
00096
00097 reference operator[](size_type i) const throw ()
00098 { return field(*this, i); }
00099 reference operator[](int i) const throw ()
00100 { return operator[](size_type(i)); }
00101 reference operator[](const char[]) const;
00102 reference operator[](const PGSTD::string &s) const
00103 { return operator[](s.c_str()); }
00104 reference at(size_type) const throw (PGSTD::out_of_range);
00105 reference at(int i) const throw (PGSTD::out_of_range)
00106 { return at(size_type(i)); }
00107 reference at(const char[]) const;
00108 reference at(const PGSTD::string &s) const
00109 { return at(s.c_str()); }
00110
00111 size_type size() const throw () { return m_Home->columns(); }
00112
00113 void swap(tuple &) throw ();
00114
00115 result::size_type rownumber() const throw () { return m_Index; }
00116
00118 size_type column_number(const PGSTD::string &ColName) const
00119 { return m_Home->column_number(ColName); }
00120
00122 size_type column_number(const char ColName[]) const
00123 { return m_Home->column_number(ColName); }
00124
00126 oid column_type(size_type ColNum) const
00127 { return m_Home->column_type(ColNum); }
00128
00130 oid column_type(int ColNum) const
00131 { return column_type(size_type(ColNum)); }
00132
00134 oid column_type(const PGSTD::string &ColName) const
00135 { return column_type(column_number(ColName)); }
00136
00138 oid column_type(const char ColName[]) const
00139 { return column_type(column_number(ColName)); }
00140
00141 result::size_type num() const { return rownumber(); }
00142
00143 #ifdef PQXX_HAVE_PQFTABLE
00144 oid column_table(size_type ColNum) const
00145 { return m_Home->column_table(ColNum); }
00146 oid column_table(int ColNum) const
00147 { return column_table(size_type(ColNum)); }
00148 oid column_table(const PGSTD::string &ColName) const
00149 { return column_table(column_number(ColName)); }
00150 #endif
00151
00152
00153 #ifdef PQXX_DEPRECATED_HEADERS
00154
00155 result::size_type Row() const { return rownumber(); }
00156
00158 size_type ColumnNumber(const PGSTD::string &ColName) const
00159 { return column_number(ColName); }
00160
00162 size_type ColumnNumber(const char ColName[]) const
00163 { return column_number(ColName); }
00164 #endif
00165
00166 protected:
00167 friend class field;
00168 const result *m_Home;
00169 result::size_type m_Index;
00170
00171
00172 tuple();
00173 };
00174
00176
00179 class PQXX_LIBEXPORT field
00180 {
00181 public:
00182 typedef size_t size_type;
00183
00185
00189 field(const tuple &T, tuple::size_type C) throw () :
00190 m_tup(T), m_col(C) {}
00191
00193
00209 bool operator==(const field &) const;
00210
00212
00214 bool operator!=(const field &rhs) const {return !operator==(rhs);}
00215
00217
00222 const char *c_str() const { return home()->GetValue(idx(),col()); }
00223
00225 const char *name() const { return home()->column_name(col()); }
00226
00228 oid type() const { return home()->column_type(col()); }
00229
00230 #ifdef PQXX_HAVE_PQFTABLE
00231
00232
00234 oid table() const { return home()->column_table(col()); }
00235 #endif
00236
00238 template<typename T> bool to(T &Obj) const
00239 {
00240 if (is_null()) return false;
00241 try
00242 {
00243 from_string(c_str(), Obj);
00244 }
00245 catch (const PGSTD::exception &e)
00246 {
00247 throw PGSTD::domain_error("Error reading field " +
00248 PGSTD::string(name()) + ": " +
00249 e.what());
00250 }
00251 return true;
00252 }
00253
00255 template<typename T> bool operator>>(T &Obj) const
00256 { return to(Obj); }
00257
00258 #ifdef PQXX_NO_PARTIAL_CLASS_TEMPLATE_SPECIALISATION
00259
00260 template<> bool to<PGSTD::string>(PGSTD::string &Obj) const;
00261
00263
00266 template<> bool to<const char *>(const char *&Obj) const;
00267 #endif
00268
00270 template<typename T> bool to(T &Obj, const T &Default) const
00271 {
00272 const bool NotNull = to(Obj);
00273 if (!NotNull) Obj = Default;
00274 return NotNull;
00275 }
00276
00278
00281 template<typename T> T as(const T &Default) const
00282 {
00283 T Obj;
00284 to(Obj, Default);
00285 return Obj;
00286 }
00287
00289 template<typename T> T as() const
00290 {
00291 T Obj;
00292 const bool NotNull = to(Obj);
00293 if (!NotNull) throw PGSTD::domain_error("Attempt to read null field");
00294 return Obj;
00295 }
00296
00297 bool is_null() const { return home()->GetIsNull(idx(), col()); }
00298 size_type size() const throw ()
00299 { return home()->GetLength(idx(),col()); }
00300 tuple::size_type num() const { return col(); }
00301
00302 #ifdef PQXX_DEPRECATED_HEADERS
00303
00304 const char *Name() const {return name();}
00305 #endif
00306
00307 private:
00308 const result *home() const throw () { return m_tup.m_Home; }
00309 result::size_type idx() const throw () { return m_tup.m_Index; }
00310
00311 protected:
00312 const tuple::size_type col() const throw () { return m_col; }
00313 tuple m_tup;
00314 tuple::size_type m_col;
00315 };
00316
00317 typedef PGSTD::iterator<PGSTD::random_access_iterator_tag,
00318 const tuple,
00319 result::difference_type,
00320 const_iterator,
00321 tuple> const_iterator_base;
00322
00324
00328 class PQXX_LIBEXPORT const_iterator :
00329 public const_iterator_base,
00330 public tuple
00331 {
00332 public:
00333 typedef const tuple *pointer;
00334 typedef tuple reference;
00335 typedef result::size_type size_type;
00336 typedef result::difference_type difference_type;
00337
00338 const_iterator() throw () : tuple(0,0) {}
00339 const_iterator(const tuple &t) throw () : tuple(t) {}
00340
00352 pointer operator->() const { return this; }
00353 reference operator*() const { return tuple(*this); }
00354
00355 const_iterator operator++(int);
00356 const_iterator &operator++() { ++m_Index; return *this; }
00357 const_iterator operator--(int);
00358 const_iterator &operator--() { --m_Index; return *this; }
00359
00360 const_iterator &operator+=(difference_type i)
00361 { m_Index+=i; return *this; }
00362 const_iterator &operator-=(difference_type i)
00363 { m_Index-=i; return *this; }
00364
00365 bool operator==(const const_iterator &i) const
00366 {return m_Index==i.m_Index;}
00367 bool operator!=(const const_iterator &i) const
00368 {return m_Index!=i.m_Index;}
00369 bool operator<(const const_iterator &i) const
00370 {return m_Index<i.m_Index;}
00371 bool operator<=(const const_iterator &i) const
00372 {return m_Index<=i.m_Index;}
00373 bool operator>(const const_iterator &i) const
00374 {return m_Index>i.m_Index;}
00375 bool operator>=(const const_iterator &i) const
00376 {return m_Index>=i.m_Index;}
00377
00378 inline const_iterator operator+(difference_type) const;
00379 friend const_iterator
00380 operator+(difference_type, const_iterator);
00381 inline const_iterator operator-(difference_type) const;
00382 inline difference_type operator-(const_iterator) const;
00383
00384 private:
00385 friend class pqxx::result;
00386 const_iterator(const pqxx::result *r, result::size_type i) throw () :
00387 tuple(r, i) {}
00388 };
00389
00390 class PQXX_LIBEXPORT const_reverse_iterator : private const_iterator
00391 {
00392 public:
00393 typedef const_iterator iterator_type;
00394 using iterator_type::iterator_category;
00395 using iterator_type::difference_type;
00396 using iterator_type::pointer;
00397 #ifndef _MSC_VER
00398 using iterator_type::value_type;
00399 using iterator_type::reference;
00400 #else
00401
00402 typedef const tuple &reference;
00403 typedef tuple value_type;
00404 #endif
00405
00406 const_reverse_iterator(const const_reverse_iterator &rhs) :
00407 const_iterator(rhs), m_tmp(rhs) {}
00408 explicit const_reverse_iterator(const const_iterator &rhs) :
00409 const_iterator(rhs), m_tmp() {}
00410
00411 iterator_type base() const throw () { return *this; }
00412
00413 const_reverse_iterator &operator=(const const_reverse_iterator &r)
00414 { iterator_type::operator=(r); return *this; }
00415 pointer operator->() const throw ()
00416 { m_tmp=*this; --m_tmp; return &m_tmp; }
00417 reference operator*() const throw () { return *operator->(); }
00418 const_reverse_iterator operator++()
00419 { iterator_type::operator--(); return *this; }
00420 const_reverse_iterator operator++(int);
00421 const_reverse_iterator &operator--()
00422 { iterator_type::operator++(); return *this; }
00423 const_reverse_iterator operator--(int);
00424 const_reverse_iterator operator+(difference_type i) const
00425 { return const_reverse_iterator(iterator_type(*this)-i); }
00426 const_reverse_iterator &operator+=(difference_type i)
00427 { iterator_type::operator-=(i); return *this; }
00428 const_reverse_iterator operator-(difference_type i)
00429 { return const_reverse_iterator(iterator_type(*this)+i); }
00430 const_reverse_iterator &operator-=(difference_type i)
00431 { iterator_type::operator+=(i); return *this; }
00432
00433 bool operator==(const const_reverse_iterator &rhs) const throw ()
00434 { return iterator_type::operator==(rhs); }
00435 bool operator!=(const const_reverse_iterator &rhs) const throw ()
00436 { return !operator==(rhs); }
00437
00438 bool operator<(const const_reverse_iterator &rhs) const
00439 { return iterator_type::operator>(rhs); }
00440 bool operator<=(const const_reverse_iterator &rhs) const
00441 { return iterator_type::operator>=(rhs); }
00442 bool operator>(const const_reverse_iterator &rhs) const
00443 { return iterator_type::operator<(rhs); }
00444 bool operator>=(const const_reverse_iterator &rhs) const
00445 { return iterator_type::operator<=(rhs); }
00446 difference_type operator-(const const_reverse_iterator &rhs) const
00447 { return rhs.base() - base(); }
00448
00449 private:
00451
00456 mutable iterator_type m_tmp;
00457 };
00458
00459 class PQXX_LIBEXPORT const_fielditerator :
00460 public PGSTD::iterator<PGSTD::random_access_iterator_tag,
00461 const field,
00462 tuple::size_type>,
00463 public field
00464 {
00465 typedef PGSTD::iterator<PGSTD::random_access_iterator_tag,
00466 const field,
00467 tuple::size_type> it;
00468 public:
00469 using it::pointer;
00470 typedef tuple::size_type size_type;
00471 typedef tuple::difference_type difference_type;
00472 typedef field reference;
00473
00474 const_fielditerator(const tuple &T, tuple::size_type C) throw () :
00475 field(T, C) {}
00476 const_fielditerator(const field &F) throw () : field(F) {}
00477
00478 pointer operator->() const { return this; }
00479 reference operator*() const { return field(*this); }
00480
00481 const_fielditerator operator++(int);
00482 const_fielditerator &operator++() { ++m_col; return *this; }
00483 const_fielditerator operator--(int);
00484 const_fielditerator &operator--() { --m_col; return *this; }
00485
00486 const_fielditerator &operator+=(difference_type i)
00487 { m_col+=i; return *this; }
00488 const_fielditerator &operator-=(difference_type i)
00489 { m_col-=i; return *this; }
00490
00491 bool operator==(const const_fielditerator &i) const
00492 {return col()==i.col();}
00493 bool operator!=(const const_fielditerator &i) const
00494 {return col()!=i.col();}
00495 bool operator<(const const_fielditerator &i) const
00496 {return col()<i.col();}
00497 bool operator<=(const const_fielditerator &i) const
00498 {return col()<=i.col();}
00499 bool operator>(const const_fielditerator &i) const
00500 {return col()>i.col();}
00501 bool operator>=(const const_fielditerator &i) const
00502 {return col()>=i.col();}
00503
00504 inline const_fielditerator operator+(difference_type) const;
00505
00506 friend const_fielditerator operator+(difference_type,
00507 const_fielditerator);
00508
00509 inline const_fielditerator operator-(difference_type) const;
00510 inline difference_type operator-(const_fielditerator) const;
00511 };
00512
00513 class PQXX_LIBEXPORT const_reverse_fielditerator : private const_fielditerator
00514 {
00515 public:
00516 typedef const_fielditerator iterator_type;
00517 using iterator_type::iterator_category;
00518 using iterator_type::difference_type;
00519 using iterator_type::pointer;
00520 #ifndef _MSC_VER
00521 using iterator_type::value_type;
00522 using iterator_type::reference;
00523 #else
00524
00525 typedef field value_type;
00526 typedef const field &reference;
00527 #endif
00528
00529 iterator_type base() const throw () { return *this; }
00530 const_reverse_fielditerator(const const_reverse_fielditerator &rhs)
00531 : const_fielditerator(rhs), m_tmp(rhs.m_tmp) {}
00532 explicit
00533 const_reverse_fielditerator(const const_fielditerator &rhs) :
00534 const_fielditerator(rhs), m_tmp(rhs) {}
00535
00536 const_reverse_fielditerator &
00537 operator=(const const_reverse_fielditerator &r)
00538 { iterator_type::operator=(r); return *this; }
00539 pointer operator->() const throw ()
00540 { m_tmp = *this; --m_tmp; return &m_tmp; }
00541 reference operator*() const throw () { return *operator->(); }
00542 const_reverse_fielditerator operator++()
00543 { iterator_type::operator--(); return *this; }
00544 const_reverse_fielditerator operator++(int);
00545 const_reverse_fielditerator &operator--()
00546 { iterator_type::operator++(); return *this; }
00547 const_reverse_fielditerator operator--(int);
00548 const_reverse_fielditerator operator+(difference_type i) const
00549 { return const_reverse_fielditerator(iterator_type(*this)-i); }
00550 const_reverse_fielditerator &operator+=(difference_type i)
00551 { iterator_type::operator-=(i); return *this; }
00552 const_reverse_fielditerator operator-(difference_type i)
00553 { return const_reverse_fielditerator(iterator_type(*this)+i); }
00554 const_reverse_fielditerator &operator-=(difference_type i)
00555 { iterator_type::operator+=(i); return *this; }
00556
00557 bool
00558 operator==(const const_reverse_fielditerator &rhs) const throw ()
00559 { return iterator_type::operator==(rhs); }
00560 bool
00561 operator!=(const const_reverse_fielditerator &rhs) const throw ()
00562 { return !operator==(rhs); }
00563
00564
00565 bool operator<(const const_reverse_fielditerator &rhs) const
00566 { return iterator_type::operator>(rhs); }
00567 bool operator<=(const const_reverse_fielditerator &rhs) const
00568 { return iterator_type::operator>=(rhs); }
00569 bool operator>(const const_reverse_fielditerator &rhs) const
00570 { return iterator_type::operator<(rhs); }
00571 bool operator>=(const const_reverse_fielditerator &rhs) const
00572 { return iterator_type::operator<=(rhs); }
00573 difference_type
00574 operator-(const const_reverse_fielditerator &rhs) const
00575 { return rhs.base() - base(); }
00576
00577 private:
00579
00584 mutable iterator_type m_tmp;
00585 };
00586
00587
00588 result() throw () : super() {}
00589 result(const result &rhs) throw () : super(rhs) {}
00590
00591 result &operator=(const result &rhs) throw ()
00592 { super::operator=(rhs); return *this; }
00593
00594 bool operator==(const result &) const throw ();
00595 bool operator!=(const result &rhs) const throw ()
00596 { return !operator==(rhs); }
00597
00598 const_reverse_iterator rbegin() const
00599 { return const_reverse_iterator(end()); }
00600 const_reverse_iterator rend() const
00601 { return const_reverse_iterator(begin()); }
00602
00603 const_iterator begin() const throw ()
00604 { return const_iterator(this, 0); }
00605 inline const_iterator end() const throw ();
00606
00607 reference front() const throw () { return tuple(this,0); }
00608 reference back() const throw () {return tuple(this,size()-1);}
00609
00610 size_type size() const throw ()
00611 { return c_ptr() ? PQXXPQ::PQntuples(c_ptr()) : 0; }
00612 bool empty() const
00613 { return !c_ptr() || !PQXXPQ::PQntuples(c_ptr()); }
00614 size_type capacity() const throw () { return size(); }
00615
00616 void swap(result &) throw ();
00617
00618 const tuple operator[](size_type i) const throw ()
00619 { return tuple(this, i); }
00620 const tuple at(size_type) const throw (PGSTD::out_of_range);
00621
00622 using super::clear;
00623
00625 tuple::size_type columns() const throw ()
00626 { return PQnfields(c_ptr()); }
00627
00629 tuple::size_type column_number(const char ColName[]) const;
00630
00632 tuple::size_type column_number(const PGSTD::string &Name) const
00633 {return column_number(Name.c_str());}
00634
00636 const char *column_name(tuple::size_type Number) const;
00637
00639 oid column_type(tuple::size_type ColNum) const;
00641 oid column_type(int ColNum) const
00642 { return column_type(tuple::size_type(ColNum)); }
00643
00645 oid column_type(const PGSTD::string &ColName) const
00646 { return column_type(column_number(ColName)); }
00647
00649 oid column_type(const char ColName[]) const
00650 { return column_type(column_number(ColName)); }
00651
00652 #ifdef PQXX_HAVE_PQFTABLE
00653
00654 oid column_table(tuple::size_type ColNum) const;
00656 oid column_table(int ColNum) const
00657 { return column_table(tuple::size_type(ColNum)); }
00658
00660 oid column_table(const PGSTD::string &ColName) const
00661 { return column_table(column_number(ColName)); }
00662 #endif
00663
00665
00668 oid inserted_oid() const { return PQoidValue(c_ptr()); }
00669
00670
00672
00675 size_type affected_rows() const;
00676
00677
00678 #ifdef PQXX_DEPRECATED_HEADERS
00679
00680 typedef tuple Tuple;
00682 typedef field Field;
00684 oid InsertedOid() const { return inserted_oid(); }
00686 size_type AffectedRows() const { return affected_rows(); }
00688 tuple::size_type Columns() const { return columns(); }
00690 tuple::size_type ColumnNumber(const char Name[]) const
00691 {return PQfnumber(c_ptr(),Name);}
00693 tuple::size_type ColumnNumber(const PGSTD::string &Name) const
00694 {return ColumnNumber(Name.c_str());}
00696 const char *ColumnName(tuple::size_type Number) const
00697 {return PQfname(c_ptr(),Number);}
00698 #endif
00699
00700
00701 private:
00702 friend class pqxx::result::field;
00703 const char *GetValue(size_type Row, tuple::size_type Col) const;
00704 bool GetIsNull(size_type Row, tuple::size_type Col) const;
00705 field::size_type GetLength(size_type Row, tuple::size_type Col) const;
00706
00707 friend class connection_base;
00708 friend class pipeline;
00709 explicit result(PQXXPQ::PGresult *rhs) throw () : super(rhs) {}
00710 result &operator=(PQXXPQ::PGresult *rhs) throw ()
00711 { super::operator=(rhs); return *this; }
00712 bool operator!() const throw () { return !c_ptr(); }
00713 operator bool() const throw () { return c_ptr() != 0; }
00714 void CheckStatus(const PGSTD::string &Query) const;
00715 void CheckStatus(const char Query[]) const;
00716 int errorposition() const throw ();
00717 PGSTD::string StatusError() const;
00718
00719 friend class Cursor;
00720 const char *CmdStatus() const throw () { return PQcmdStatus(c_ptr()); }
00721 };
00722
00723
00725
00744 template<typename STREAM>
00745 inline STREAM &operator<<(STREAM &S, const pqxx::result::field &F)
00746 {
00747 S.write(F.c_str(), F.size());
00748 return S;
00749 }
00750
00751
00753 template<typename T>
00754 inline void from_string(const result::field &F, T &Obj)
00755 { from_string(F.c_str(), Obj); }
00756
00758 template<>
00759 inline PGSTD::string to_string(const result::field &Obj)
00760 { return to_string(Obj.c_str()); }
00761
00762
00764 template<>
00765 inline bool result::field::to<PGSTD::string>(PGSTD::string &Obj) const
00766 {
00767 if (is_null()) return false;
00768 Obj = c_str();
00769 return true;
00770 }
00771
00773
00778 template<>
00779 inline bool result::field::to<const char *>(const char *&Obj) const
00780 {
00781 if (is_null()) return false;
00782 Obj = c_str();
00783 return true;
00784 }
00785
00786
00787 inline result::tuple::const_reverse_iterator result::tuple::rbegin() const
00788 { return const_reverse_fielditerator(end()); }
00789 inline result::tuple::const_reverse_iterator result::tuple::rend() const
00790 { return const_reverse_fielditerator(begin()); }
00791
00792 inline result::const_iterator
00793 result::const_iterator::operator+(difference_type o) const
00794 { return const_iterator(m_Home, m_Index + o); }
00795
00796 inline result::const_iterator
00797 operator+(result::const_iterator::difference_type o, result::const_iterator i)
00798 { return i + o; }
00799
00800 inline result::const_iterator
00801 result::const_iterator::operator-(difference_type o) const
00802 { return const_iterator(m_Home, m_Index - o); }
00803
00804 inline result::const_iterator::difference_type
00805 result::const_iterator::operator-(const_iterator i) const
00806 { return num()-i.num(); }
00807
00808 inline result::const_iterator result::end() const throw ()
00809 { return const_iterator(this, size()); }
00810
00811
00812 inline result::const_reverse_iterator
00813 operator+(result::const_reverse_iterator::difference_type n,
00814 const result::const_reverse_iterator &i)
00815 { return result::const_reverse_iterator(i.base() - n); }
00816
00817 inline result::const_fielditerator
00818 result::const_fielditerator::operator+(difference_type o) const
00819 { return const_fielditerator(m_tup, col() + o); }
00820
00821 inline result::const_fielditerator
00822 operator+(result::const_fielditerator::difference_type o,
00823 result::const_fielditerator i)
00824 { return i + o; }
00825
00826 inline result::const_fielditerator
00827 result::const_fielditerator::operator-(difference_type o) const
00828 { return const_fielditerator(m_tup, col() - o); }
00829
00830 inline result::const_fielditerator::difference_type
00831 result::const_fielditerator::operator-(const_fielditerator i) const
00832 { return num()-i.num(); }
00833
00834
00835 template<typename CHAR=char, typename TRAITS=PGSTD::char_traits<CHAR> >
00836 class field_streambuf :
00837 #ifdef PQXX_HAVE_STREAMBUF
00838 public PGSTD::basic_streambuf<CHAR, TRAITS>
00839 #else
00840 public PGSTD::streambuf
00841 #endif
00842 {
00843 public:
00844 typedef CHAR char_type;
00845 typedef TRAITS traits_type;
00846 typedef typename traits_type::int_type int_type;
00847 #ifdef PQXX_HAVE_STREAMBUF
00848 typedef typename traits_type::pos_type pos_type;
00849 typedef typename traits_type::off_type off_type;
00850 #else
00851 typedef streamoff off_type;
00852 typedef streampos pos_type;
00853 #endif
00854 typedef PGSTD::ios::openmode openmode;
00855 typedef PGSTD::ios::seekdir seekdir;
00856
00857 explicit field_streambuf(const result::field &F) :
00858 m_Field(F)
00859 {
00860 initialize();
00861 }
00862
00863 #ifdef PQXX_HAVE_STREAMBUF
00864 protected:
00865 #endif
00866 virtual int sync() { return traits_type::eof(); }
00867
00868 protected:
00869 virtual pos_type seekoff(off_type, seekdir, openmode)
00870 { return traits_type::eof(); }
00871 virtual pos_type seekpos(pos_type, openmode) {return traits_type::eof();}
00872 virtual int_type overflow(int_type) { return traits_type::eof(); }
00873 virtual int_type underflow() { return traits_type::eof(); }
00874
00875 private:
00876 const result::field &m_Field;
00877
00878 int_type initialize()
00879 {
00880 char_type *G =
00881 reinterpret_cast<char_type *>(const_cast<char *>(m_Field.c_str()));
00882 setg(G, G, G + m_Field.size());
00883 return m_Field.size();
00884 }
00885 };
00886
00887
00889
00897 template<typename CHAR=char, typename TRAITS=PGSTD::char_traits<CHAR> >
00898 class basic_fieldstream :
00899 #ifdef PQXX_HAVE_STREAMBUF
00900 public PGSTD::basic_istream<CHAR, TRAITS>
00901 #else
00902 public PGSTD::istream
00903 #endif
00904 {
00905 #ifdef PQXX_HAVE_STREAMBUF
00906 typedef PGSTD::basic_istream<CHAR, TRAITS> super;
00907 #else
00908 typedef PGSTD::istream super;
00909 #endif
00910
00911 public:
00912 typedef CHAR char_type;
00913 typedef TRAITS traits_type;
00914 typedef typename traits_type::int_type int_type;
00915 typedef typename traits_type::pos_type pos_type;
00916 typedef typename traits_type::off_type off_type;
00917
00918 basic_fieldstream(const result::field &F) : super(&m_Buf), m_Buf(F) { }
00919
00920 private:
00921 field_streambuf<CHAR, TRAITS> m_Buf;
00922 };
00923
00924 typedef basic_fieldstream<char> fieldstream;
00925
00926 }
00927
00928
00929
00930
00931
00932
00933
00934
00935
00936
00937
00938
00939
00940
00941
00942
00943