00001
00002
00003 #ifndef OBJECTPARSER_H
00004 #define OBJECTPARSER_H
00005
00006 #include <iostream>
00007 #include <vector>
00008 #include "Object.h"
00009 #include <map>
00010 #include <string>
00011
00012 namespace FD {
00013
00014 inline bool isValidType (std::istream &in, std::string expectedType, bool binary=false);
00015
00016 template <class T>
00017 inline std::ostream &operator << (std::ostream &out, const RCPtr<T> &ref)
00018 {
00019 out << *ref;
00020 return out;
00021 }
00022
00023 template <class T>
00024 inline std::ostream &operator << (std::ostream &out, const std::vector<T> &v)
00025 {
00026 out << "<Vector ";
00027 for (int i=0; i < v.size(); i++)
00028 {
00029 out << " " << v[i];
00030 }
00031 out << " > ";
00032 return out;
00033 }
00034
00035 template <class T>
00036 inline std::ostream &operator << (std::ostream &out, const std::vector<T*> &v)
00037 {
00038 out << "<Vector ";
00039 for (int i=0; i < v.size(); i++)
00040 {
00041 out << " " << *(v[i]);
00042 }
00043 out << " > ";
00044 return out;
00045 }
00046
00047
00048 template <class T>
00049 inline std::istream &operator >> (std::istream &in, std::vector<T> &v)
00050 {
00051 int items_found=0;
00052
00053 if (!isValidType(in,"Vector"))
00054 return in;
00055
00056 while (1)
00057 {
00058 char ch=' ';
00059 while (ch == ' ')
00060 {
00061 in >> ch;
00062 if (ch == '>')
00063 {
00064 return in;
00065 } else if (ch != ' ') {
00066 in.putback(ch);
00067 }
00068 if (in.fail())
00069 throw new GeneralException("Error reading vector: '>' expected", __FILE__, __LINE__);
00070 }
00071 T tmp;
00072 in >> tmp;
00073 if (in.fail())
00074 throw new GeneralException("Error reading vector", __FILE__, __LINE__);
00075 v.push_back(tmp);
00076 }
00077 }
00078
00079 template <class T>
00080 inline std::istream &operator >> (std::istream &in, std::vector<T*> &v)
00081 {
00082 int items_found=0;
00083
00084 if (!isValidType(in,"Vector"))
00085 return in;
00086
00087 while (1)
00088 {
00089 char ch=' ';
00090 while (ch == ' ')
00091 {
00092 in >> ch;
00093 if (ch == '>')
00094 {
00095 return in;
00096 } else if (ch != ' ') {
00097 in.putback(ch);
00098 }
00099 if (in.fail())
00100 throw new GeneralException("Error reading vector: '>' expected", __FILE__, __LINE__);
00101 }
00102 T *tmp = new T;
00103 in >> *tmp;
00104 if (in.fail())
00105 throw new GeneralException("Error reading vector", __FILE__, __LINE__);
00106 v.push_back(tmp);
00107 }
00108 }
00109
00110
00111 class ParsingException : public BaseException{
00112 public:
00113 ParsingException (std::string _message)
00114 : message(_message)
00115 {}
00116 void print(std::ostream &out=std::cerr) {out << message << std::endl;}
00117 protected:
00118 std::string message;
00119 };
00120
00121
00122 inline bool isValidType (std::istream &in, std::string expectedType, bool binary)
00123 {
00124 char ch;
00125 in >> ch;
00126 if ((ch == '<' && !binary) || (ch == '{' && binary))
00127 {
00128 std::string type;
00129 in >> type;
00130 if (type != expectedType)
00131 throw new ParsingException ("ObjectParser::isValidType : Parser expected type " + expectedType + " and got " + type);
00132 } else {
00133 in.putback(ch);
00134 in.clear(std::ios::failbit);
00135 return false;
00136 }
00137 return true;
00138 }
00139
00140
00141
00142
00143 template <class T>
00144 inline std::istream &operator >> (std::istream &in, RCPtr<T> &o)
00145 {
00146 char ch;
00147 in >> ch;
00148 if (ch == '<')
00149 {
00150 std::string type;
00151 in >> type;
00152 o = Object::newObject(type);
00153 o->readFrom(in);
00154 } else if (ch == '{')
00155 {
00156 std::string type;
00157 in >> type;
00158 o = Object::newObject(type);
00159 int dummyCount=0;
00160 char dummy;
00161 do {
00162 in >> dummy;
00163 if (dummyCount > 5)
00164 throw new ParsingException("Cannot find sync \"|\" symbol for unserialize");
00165 dummyCount++;
00166 } while(dummy != '|');
00167 o->unserialize(in);
00168 } else {
00169 throw new ParsingException(std::string("Expected '<' or '{' (got '") + ch + "')");
00170 }
00171
00172 return in;
00173 }
00174
00175 template <class T>
00176 inline std::istream &operator >> (std::istream &in, T* &o)
00177 {
00178 RCPtr<T> obj;
00179 in >> obj;
00180 o = obj.detach();
00181 return in;
00182 }
00183
00184 }
00185
00186 #endif