Main Page | Namespace List | Class Hierarchy | Alphabetical List | Class List | File List | Namespace Members | Class Members | File Members

filterstreambuf.h

Go to the documentation of this file.
00001 #ifndef DV_UTIL_FILTERSTREAMBUF_H 00002 #define DV_UTIL_FILTERSTREAMBUF_H 00003 // $Id: filterstreambuf.h,v 1.6 2003/08/05 13:02:07 dvermeir Exp $ 00004 00005 #include <iostream> 00006 // #include <streambuf> 00007 00008 /** \file 00009 * The Dv::Util::filterstreambuf class is a template class that 00010 * is used to define Dv::Util::filterstream objects. 00011 */ 00012 namespace Dv { 00013 namespace Util { 00014 /** 00015 * A streambuf specialization that cooperates with a filter class object. 00016 * A filterstreambuf does not buffer data, but immediately passes them on 00017 * (resp. obtains them from) to the filter. 00018 * 00019 * The requirements for the Filter template parameter are as follows: 00020 * 00021 * \code 00022 * class Filter { 00023 * public: 00024 * int get(); // return next input char or Traits::eof 00025 * int put(int c); // output c if c!=EOF, return EOF if error 00026 * int sync(); // synchronize filter, return 0 (ok) or -1 (EOF) 00027 * void close(); // close filter, no obligations.. 00028 * ios_base::iostate state(); // return status of filter 00029 * }; 00030 * \endcode 00031 * Here, \a state() is not used by filterstreambuf but may be 00032 * convenient for streams based on a filterstreambuf: the 00033 * constructor can use basic_ios::clear(filter.state()) to inherit 00034 * the initial state of the filter. 00035 * 00036 * \see Dv::Util::teestream 00037 */ 00038 template <class Filter> 00039 class filterstreambuf: public std::streambuf { 00040 public: 00041 /** 00042 * The constructor remembers the filter to which I/O will be forwarded. 00043 * \param filter to which I/O operations will be forwarded. 00044 * \warning The filter is not copied, the management of the filter 00045 * is not the filterstreambuf's responsibility (only a reference 00046 * to the filter is kept). 00047 */ 00048 explicit filterstreambuf(Filter& filter): filter_(filter) { 00049 setg(inbuf_,inbuf_+1,inbuf_+1); // very small input buffer 00050 setp(outbuf_,outbuf_); // no output buffer 00051 } 00052 /** 00053 * This is already virtual in streambuf. 00054 */ 00055 virtual ~filterstreambuf() {} 00056 /** 00057 * \return underlying filter (const version). 00058 */ 00059 const Filter& filter() const { return filter_; } 00060 /** 00061 * \return underlying filter (non-const version). 00062 */ 00063 Filter& filter() { return filter_; } 00064 00065 /** 00066 * Set underlying filter. 00067 * \param filter to which I/O operations will be forwarded. 00068 * \warning The filter is not copied, the management of the filter 00069 * is not the filterstreambuf's responsibility. 00070 */ 00071 filterstreambuf& filter(Filter& filter) { filter_ = filter; return *this; } 00072 00073 /** 00074 * Close -- indicate intention not to use the filter anymore. 00075 * \return return status of Dv::Util::filterstreambuf::sync. 00076 */ 00077 bool close() { int tmp=sync(); filter_.close(); return tmp; } 00078 00079 /** 00080 * Override iostream::sync(). 00081 * \return return status of \a filter_.sync() . 00082 */ 00083 virtual int sync() { return filter_.sync(); } 00084 00085 protected: 00086 /** 00087 * Override iostream::underflow(). 00088 * \return next input char or EOF 00089 */ 00090 virtual int underflow() { 00091 if (gptr()<egptr()) // buffer not empty 00092 return *gptr(); 00093 if ( (inbuf_[0] = filter_.get()) != EOF) 00094 setg(inbuf_,inbuf_,inbuf_+1); 00095 return inbuf_[0]; 00096 } 00097 /** 00098 * Override iostream::overflow(). 00099 * \param c next char to put 00100 * \return status of filter_.put(c) 00101 */ 00102 virtual int overflow(int c) { return filter_.put(c); } 00103 00104 private: 00105 Filter& filter_; 00106 char inbuf_[1]; 00107 char outbuf_[1]; // unused 00108 }; 00109 00110 }} 00111 #endif

dvutil-0.13.15 [30 December, 2004]