00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00022
00023 #ifndef LEMON_BITS_ITEM_WRITER_H
00024 #define LEMON_BITS_ITEM_WRITER_H
00025
00026 #include <iostream>
00027 #include <string>
00028
00029 #include <vector>
00030 #include <deque>
00031 #include <list>
00032 #include <set>
00033
00034 namespace lemon {
00035
00036 template <typename Value>
00037 class DefaultWriter;
00038
00045 class QuotedStringWriter {
00046 public:
00047 typedef std::string Value;
00048
00053 QuotedStringWriter(bool _escaped = true) : escaped(_escaped) {}
00054
00058 void write(std::ostream& os, const std::string& value) const {
00059 os << "\"";
00060 if (escaped) {
00061 std::ostringstream ls;
00062 for (int i = 0; i < (int)value.size(); ++i) {
00063 writeEscape(ls, value[i]);
00064 }
00065 os << ls.str();
00066 } else {
00067 os << value;
00068 }
00069 os << "\"";
00070 }
00071
00072 private:
00073
00074 static void writeEscape(std::ostream& os, char c) {
00075 switch (c) {
00076 case '\\':
00077 os << "\\\\";
00078 return;
00079 case '\"':
00080 os << "\\\"";
00081 return;
00082 case '\'':
00083 os << "\\\'";
00084 return;
00085 case '\?':
00086 os << "\\\?";
00087 return;
00088 case '\a':
00089 os << "\\a";
00090 return;
00091 case '\b':
00092 os << "\\b";
00093 return;
00094 case '\f':
00095 os << "\\f";
00096 return;
00097 case '\r':
00098 os << "\\r";
00099 return;
00100 case '\n':
00101 os << "\\n";
00102 return;
00103 case '\t':
00104 os << "\\t";
00105 return;
00106 case '\v':
00107 os << "\\v";
00108 return;
00109 default:
00110 if (c < 0x20) {
00111 os << '\\' << std::oct << (int)c;
00112 } else {
00113 os << c;
00114 }
00115 return;
00116 }
00117 }
00118 private:
00119 bool escaped;
00120 };
00121
00128 class QuotedCharArrayWriter {
00129 public:
00130 typedef const char* Value;
00131
00136 QuotedCharArrayWriter(bool _escaped = true) : escaped(_escaped) {}
00137
00141 void write(std::ostream& os, const char* value) const {
00142 QuotedStringWriter(escaped).write(os, std::string(value));
00143 }
00144
00145 private:
00146 bool escaped;
00147 };
00148
00149
00159 template <
00160 typename _Container,
00161 typename _ItemWriter = DefaultWriter<typename _Container::value_type>
00162 >
00163 class IterableWriter {
00164 public:
00165 typedef _Container Value;
00166 typedef _ItemWriter ItemWriter;
00167
00168 private:
00169
00170 ItemWriter item_writer;
00171
00172 public:
00173
00174 IterableWriter(const ItemWriter& _item_writer = ItemWriter())
00175 : item_writer(_item_writer) {}
00176
00180 void write(std::ostream& os, const Value& value) const {
00181 typename Value::const_iterator it;
00182 os << '(';
00183 for (it = value.begin(); it != value.end(); ++it) {
00184 item_writer.write(os, *it);
00185 os << ' ';
00186 }
00187 os << ')';
00188 }
00189
00190 };
00191
00199 template <typename _Pair,
00200 typename _FirstWriter =
00201 DefaultWriter<typename _Pair::first_type>,
00202 typename _SecondWriter =
00203 DefaultWriter<typename _Pair::second_type> >
00204 class PairWriter {
00205 public:
00206
00207 typedef _Pair Value;
00208
00209 typedef _FirstWriter FirstWriter;
00210 typedef _SecondWriter SecondWriter;
00211
00212 private:
00213
00214 FirstWriter first_writer;
00215 SecondWriter second_writer;
00216
00217 public:
00218
00222 PairWriter(const FirstWriter& _first_writer = FirstWriter(),
00223 const SecondWriter& _second_writer = SecondWriter())
00224 : first_writer(_first_writer), second_writer(_second_writer) {}
00225
00229 void write(std::ostream& os, const Value& value) const {
00230 os << "( ";
00231 first_writer.write(os, value.first);
00232 os << " => ";
00233 second_writer.write(os, value.second);
00234 os << " )";
00235 }
00236
00237 };
00238
00247 template <typename _Value>
00248 class DefaultWriter {
00249 public:
00251 typedef _Value Value;
00255 void write(std::ostream& os, const Value& value) const {
00256 os << value;
00257 }
00258 };
00259
00260 template <>
00261 class DefaultWriter<std::string>
00262 : public QuotedStringWriter {};
00263
00264 template <int length>
00265 class DefaultWriter<char[length]>
00266 : public QuotedCharArrayWriter {};
00267
00268 template <int length>
00269 class DefaultWriter<const char[length]>
00270 : public QuotedCharArrayWriter {};
00271
00272 template <>
00273 class DefaultWriter<char*>
00274 : public QuotedCharArrayWriter {};
00275
00276 template <>
00277 class DefaultWriter<const char*>
00278 : public QuotedCharArrayWriter {};
00279
00280 template <typename Item>
00281 class DefaultWriter<std::vector<Item> >
00282 : public IterableWriter<std::vector<Item> > {};
00283
00284 template <typename Item>
00285 class DefaultWriter<std::deque<Item> >
00286 : public IterableWriter<std::deque<Item> > {};
00287
00288 template <typename Item>
00289 class DefaultWriter<std::list<Item> >
00290 : public IterableWriter<std::list<Item> > {};
00291
00292 template <typename Item>
00293 class DefaultWriter<std::set<Item> >
00294 : public IterableWriter<std::set<Item> > {};
00295
00296 template <typename Key, typename Value>
00297 class DefaultWriter<std::map<Key, Value> >
00298 : public IterableWriter<std::map<Key, Value> > {};
00299
00300 template <typename Item>
00301 class DefaultWriter<std::multiset<Item> >
00302 : public IterableWriter<std::multiset<Item> > {};
00303
00304 template <typename Key, typename Value>
00305 class DefaultWriter<std::multimap<Key, Value> >
00306 : public IterableWriter<std::multimap<Key, Value> > {};
00307
00308 template <typename First, typename Second>
00309 class DefaultWriter<std::pair<First, Second> >
00310 : public PairWriter<std::pair<First, Second> > {};
00311
00318 struct DefaultWriterTraits {
00319
00320 template <typename _Value>
00321 struct Writer : DefaultWriter<_Value> {
00322 typedef DefaultWriter<_Value> Parent;
00323 };
00324
00325 };
00326
00327 }
00328
00329 #endif