00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015 #include "stdpre.h"
00016
00017 #if HAVE_SSTREAM || !defined(__GNUC__) || (__GNUC__ >= 3)
00018
00019 #include <sstream>
00020
00021 #elif defined(__GNUC_MINOR__) && (__GNUC_MINOR__ >= 95)
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
00046
00047
00048
00049
00050
00051
00052 #include <iostream.h>
00053 #include <streambuf.h>
00054 #include <string>
00055
00056 namespace std
00057 {
00058 class stringbuf : public streambuf
00059 {
00060 public:
00061 typedef char char_type;
00062 typedef int int_type;
00063 typedef streampos pos_type;
00064 typedef streamoff off_type;
00065
00066 explicit
00067 stringbuf(int which=ios::in|ios::out)
00068 : streambuf(), mode(static_cast<ios::open_mode>(which)),
00069 stream(NULL), stream_len(0)
00070 {
00071 stringbuf_init();
00072 }
00073
00074 explicit
00075 stringbuf(const string &str, int which=ios::in|ios::out)
00076 : streambuf(), mode(static_cast<ios::open_mode>(which)),
00077 stream(NULL), stream_len(0)
00078 {
00079 if (mode & (ios::in|ios::out))
00080 {
00081 stream_len = str.size();
00082 stream = new char_type[stream_len];
00083 str.copy(stream, stream_len);
00084 }
00085 stringbuf_init();
00086 }
00087
00088 virtual
00089 ~stringbuf()
00090 {
00091 delete[] stream;
00092 }
00093
00094 string
00095 str() const
00096 {
00097 if (pbase() != 0)
00098 return string(stream, pptr()-pbase());
00099 else
00100 return string();
00101 }
00102
00103 void
00104 str(const string& str)
00105 {
00106 delete[] stream;
00107 stream_len = str.size();
00108 stream = new char_type[stream_len];
00109 str.copy(stream, stream_len);
00110 stringbuf_init();
00111 }
00112
00113 protected:
00114
00115 virtual int
00116 underflow()
00117 {
00118 return EOF;
00119 }
00120
00121 virtual int
00122 overflow(int c = EOF)
00123 {
00124 int res;
00125 if (mode & ios::out)
00126 {
00127 if (c != EOF)
00128 {
00129 streamsize old_stream_len = stream_len;
00130 stream_len += 1;
00131 char_type* new_stream = new char_type[stream_len];
00132 memcpy(new_stream, stream, old_stream_len);
00133 delete[] stream;
00134 stream = new_stream;
00135 stringbuf_sync(gptr()-eback(), pptr()-pbase());
00136 sputc(c);
00137 res = c;
00138 }
00139 else
00140 res = EOF;
00141 }
00142 else
00143 res = 0;
00144 return res;
00145 }
00146
00147 virtual streambuf*
00148 setbuf(char_type* s, streamsize n)
00149 {
00150 if (n != 0)
00151 {
00152 delete[] stream;
00153 stream = new char_type[n];
00154 memcpy(stream, s, n);
00155 stream_len = n;
00156 stringbuf_sync(0, 0);
00157 }
00158 return this;
00159 }
00160
00161 virtual pos_type
00162 seekoff(off_type off, ios::seek_dir way, int which = ios::in | ios::out)
00163 {
00164 pos_type ret = pos_type(off_type(-1));
00165 bool testin = which & ios::in && mode & ios::in;
00166 bool testout = which & ios::out && mode & ios::out;
00167 bool testboth = testin && testout && way != ios::cur;
00168
00169 if (stream_len && ((testin != testout) || testboth))
00170 {
00171 char_type* beg = stream;
00172 char_type* curi = NULL;
00173 char_type* curo = NULL;
00174 char_type* endi = NULL;
00175 char_type* endo = NULL;
00176
00177 if (testin)
00178 {
00179 curi = gptr();
00180 endi = egptr();
00181 }
00182 if (testout)
00183 {
00184 curo = pptr();
00185 endo = epptr();
00186 }
00187
00188 off_type newoffi = 0;
00189 off_type newoffo = 0;
00190 if (way == ios::beg)
00191 {
00192 newoffi = beg - curi;
00193 newoffo = beg - curo;
00194 }
00195 else if (way == ios::end)
00196 {
00197 newoffi = endi - curi;
00198 newoffo = endo - curo;
00199 }
00200
00201 if (testin && newoffi + off + curi - beg >= 0 &&
00202 endi - beg >= newoffi + off + curi - beg)
00203 {
00204 gbump(newoffi + off);
00205 ret = pos_type(newoffi + off + curi);
00206 }
00207 if (testout && newoffo + off + curo - beg >= 0 &&
00208 endo - beg >= newoffo + off + curo - beg)
00209 {
00210 pbump(newoffo + off);
00211 ret = pos_type(newoffo + off + curo);
00212 }
00213 }
00214 return ret;
00215 }
00216
00217 virtual pos_type
00218 seekpos(pos_type sp, int which = ios::in | ios::out)
00219 {
00220 pos_type ret = seekoff(sp, ios::beg, which);
00221 return ret;
00222 }
00223
00224 private:
00225 void
00226 stringbuf_sync(streamsize i, streamsize o)
00227 {
00228 if (mode & ios::in)
00229 setg(stream, stream + i, stream + stream_len);
00230 if (mode & ios::out)
00231 {
00232 setp(stream, stream + stream_len);
00233 pbump(o);
00234 }
00235 }
00236 void
00237 stringbuf_init()
00238 {
00239 if (mode & ios::ate)
00240 stringbuf_sync(0, stream_len);
00241 else
00242 stringbuf_sync(0, 0);
00243 }
00244
00245 private:
00246 ios::open_mode mode;
00247 char_type* stream;
00248 streamsize stream_len;
00249 };
00250
00251 class istringstream : public istream {
00252 public:
00253 typedef char char_type;
00254 typedef int int_type;
00255 typedef streampos pos_type;
00256 typedef streamoff off_type;
00257
00258 explicit
00259 istringstream(int which=ios::in)
00260 : istream(&sb), sb(which | ios::in)
00261 { }
00262
00263 explicit
00264 istringstream(const string& str, int which=ios::in)
00265 : istream(&sb), sb(str, which | ios::in)
00266 { }
00267
00268 stringbuf*
00269 rdbuf() const
00270 {
00271 return const_cast<stringbuf*>(&sb);
00272 }
00273
00274 string
00275 str() const
00276 {
00277 return rdbuf()->str();
00278 }
00279 void
00280 str(const string& s)
00281 {
00282 rdbuf()->str(s);
00283 }
00284 private:
00285 stringbuf sb;
00286 };
00287
00288 class ostringstream : public ostream {
00289 public:
00290 typedef char char_type;
00291 typedef int int_type;
00292 typedef streampos pos_type;
00293 typedef streamoff off_type;
00294
00295 explicit
00296 ostringstream(int which=ios::out)
00297 : ostream(&sb), sb(which | ios::out)
00298 { }
00299
00300 explicit
00301 ostringstream(const string& str, int which=ios::out)
00302 : ostream(&sb), sb(str, which | ios::out)
00303 { }
00304
00305 stringbuf*
00306 rdbuf() const
00307 {
00308 return const_cast<stringbuf*>(&sb);
00309 }
00310
00311 string
00312 str() const
00313 {
00314 return rdbuf()->str();
00315 }
00316
00317 void str(const string& s)
00318 {
00319 rdbuf()->str(s);
00320 }
00321 private:
00322 stringbuf sb;
00323 };
00324
00325 class stringstream : public iostream {
00326 public:
00327 typedef char char_type;
00328 typedef int int_type;
00329 typedef streampos pos_type;
00330 typedef streamoff off_type;
00331
00332 explicit
00333 stringstream(int which=ios::out|ios::in)
00334 : iostream(&sb), sb(which)
00335 { }
00336
00337 explicit
00338 stringstream(const string& str, int which=ios::out|ios::in)
00339 : iostream(&sb), sb(str, which)
00340 { }
00341
00342 stringbuf*
00343 rdbuf() const
00344 {
00345 return const_cast<stringbuf*>(&sb);
00346 }
00347
00348 string
00349 str() const
00350 {
00351 return rdbuf()->str();
00352 }
00353
00354 void
00355 str(const string& s)
00356 {
00357 rdbuf()->str(s);
00358 }
00359 private:
00360 stringbuf sb;
00361 };
00362 };
00363
00364 #else
00365
00366 #error "Standard C++ library is missing required sstream header."
00367
00368 #endif
00369
00370 #include "stdpost.h"
00371 #include "stdistream.h"