00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031 #ifndef MYSQLPP_TYPE_INFO_H
00032 #define MYSQLPP_TYPE_INFO_H
00033
00034 #include "defs.h"
00035
00036 #include <mysql.h>
00037
00038 #include <map>
00039 #include <typeinfo>
00040
00041 namespace mysqlpp {
00042
00043 #if !defined(DOXYGEN_IGNORE)
00044
00045
00046 class mysql_type_info;
00047 class mysql_ti_sql_type_info_lookup;
00048
00049 class mysql_ti_sql_type_info
00050 {
00051 private:
00052 friend class mysql_type_info;
00053 friend class mysql_ti_sql_type_info_lookup;
00054
00055 MYSQLPP_EXPORT mysql_ti_sql_type_info& operator=(
00056 const mysql_ti_sql_type_info& b);
00057
00058
00059
00060 mysql_ti_sql_type_info() :
00061 sql_name_(0),
00062 c_type_(0),
00063 base_type_(0),
00064 default_(false)
00065 {
00066 }
00067
00068 mysql_ti_sql_type_info(const char* s,
00069 const std::type_info& t, const unsigned char bt = 0,
00070 const bool d = false) :
00071 sql_name_(s),
00072 c_type_(&t),
00073 base_type_(bt),
00074 default_(d)
00075 {
00076 }
00077
00078 const char* sql_name_;
00079 const std::type_info* c_type_;
00080 const unsigned char base_type_;
00081 const bool default_;
00082 };
00083
00084
00085 struct type_info_cmp
00086 {
00087 bool operator() (const std::type_info* lhs,
00088 const std::type_info* rhs) const
00089 {
00090 return lhs->before(*rhs) != 0;
00091 }
00092 };
00093
00094 class mysql_ti_sql_type_info_lookup
00095 {
00096 private:
00097 friend class mysql_type_info;
00098
00099 typedef mysql_ti_sql_type_info sql_type_info;
00100
00101 MYSQLPP_EXPORT mysql_ti_sql_type_info_lookup(
00102 const sql_type_info types[], const int size);
00103
00104 const unsigned char& operator [](
00105 const std::type_info& ti) const
00106 {
00107 return map_.find(&ti)->second;
00108 }
00109
00110 std::map<const std::type_info*, unsigned char, type_info_cmp> map_;
00111 };
00112
00113 #endif // !defined(DOXYGEN_IGNORE)
00114
00115
00119 class mysql_type_info
00120 {
00121 public:
00132 mysql_type_info(unsigned char n = static_cast<unsigned char>(-1)) :
00133 num_(n)
00134 {
00135 }
00136
00142 MYSQLPP_EXPORT inline mysql_type_info(enum_field_types t,
00143 bool _unsigned, bool _null);
00144
00148 MYSQLPP_EXPORT inline mysql_type_info(const MYSQL_FIELD& f);
00149
00151 mysql_type_info(const mysql_type_info& t) :
00152 num_(t.num_)
00153 {
00154 }
00155
00160 mysql_type_info(const std::type_info& t)
00161 {
00162 num_ = lookups[t];
00163 }
00164
00170 mysql_type_info& operator =(unsigned char n)
00171 {
00172 num_ = n;
00173 return *this;
00174 }
00175
00177 mysql_type_info& operator =(const mysql_type_info& t)
00178 {
00179 num_ = t.num_;
00180 return *this;
00181 }
00182
00187 mysql_type_info& operator =(const std::type_info& t)
00188 {
00189 num_ = lookups[t];
00190 return *this;
00191 }
00192
00197 MYSQLPP_EXPORT inline const char* name() const;
00198
00202 MYSQLPP_EXPORT inline const char* sql_name() const;
00203
00208 MYSQLPP_EXPORT inline const std::type_info& c_type() const;
00209
00214 MYSQLPP_EXPORT inline const unsigned int length() const;
00215
00220 MYSQLPP_EXPORT inline const unsigned int max_length() const;
00221
00227 MYSQLPP_EXPORT inline const mysql_type_info base_type() const;
00228
00234 int id() const
00235 {
00236 return num_;
00237 }
00238
00244 MYSQLPP_EXPORT bool quote_q() const;
00245
00251 MYSQLPP_EXPORT bool escape_q() const;
00252
00257 bool before(mysql_type_info& b)
00258 {
00259 return num_ < b.num_;
00260 }
00261
00266 static const unsigned char string_type = 20;
00267
00268 unsigned int _length;
00269 unsigned int _max_length;
00270
00271 private:
00272 typedef mysql_ti_sql_type_info sql_type_info;
00273 typedef mysql_ti_sql_type_info_lookup sql_type_info_lookup;
00274
00275 MYSQLPP_EXPORT static const sql_type_info types[62];
00276
00277 MYSQLPP_EXPORT static const unsigned char offset = 0;
00278 MYSQLPP_EXPORT static const unsigned char unsigned_offset = 21;
00279 MYSQLPP_EXPORT static const unsigned char null_offset = 31;
00280 MYSQLPP_EXPORT static const unsigned char unsigned_null_offset = 52;
00281
00282 MYSQLPP_EXPORT static const sql_type_info_lookup lookups;
00283
00299 MYSQLPP_EXPORT static unsigned char type(enum_field_types t,
00300 bool _unsigned, bool _null = false);
00301
00302 const sql_type_info& deref() const
00303 {
00304 return types[num_];
00305 }
00306
00307 unsigned char num_;
00308 };
00309
00310 inline const char* mysql_type_info::name() const
00311 {
00312 return deref().c_type_->name();
00313 }
00314
00315 inline const char* mysql_type_info::sql_name() const
00316 {
00317 return deref().sql_name_;
00318 }
00319
00320 inline const unsigned int mysql_type_info::length() const
00321 {
00322 return _length;
00323 }
00324
00325 inline const unsigned int mysql_type_info::max_length() const
00326 {
00327 return _max_length;
00328 }
00329
00330 inline const std::type_info& mysql_type_info::c_type() const
00331 {
00332 return *deref().c_type_;
00333 }
00334
00335 inline const mysql_type_info mysql_type_info::base_type() const
00336 {
00337 return mysql_type_info(deref().base_type_);
00338 }
00339
00340 inline mysql_type_info::mysql_type_info(enum_field_types t,
00341 bool _unsigned, bool _null)
00342 {
00343 num_ = type(t, _unsigned, _null);
00344 }
00345
00346 inline mysql_type_info::mysql_type_info(const MYSQL_FIELD& f)
00347 {
00348 num_ = type(f.type, (f.flags & UNSIGNED_FLAG) != 0,
00349 (f.flags & NOT_NULL_FLAG) == 0);
00350 _length = f.length;
00351 _max_length = f.max_length;
00352 }
00353
00355 inline bool operator ==(const mysql_type_info& a, const mysql_type_info& b)
00356 {
00357 return a.id() == b.id();
00358 }
00359
00361 inline bool operator !=(const mysql_type_info& a, const mysql_type_info& b)
00362 {
00363 return a.id() != b.id();
00364 }
00365
00368 inline bool operator ==(const std::type_info& a, const mysql_type_info& b)
00369 {
00370 return a == b.c_type();
00371 }
00372
00375 inline bool operator !=(const std::type_info& a, const mysql_type_info& b)
00376 {
00377 return a != b.c_type();
00378 }
00379
00382 inline bool operator ==(const mysql_type_info& a, const std::type_info& b)
00383 {
00384 return a.c_type() == b;
00385 }
00386
00389 inline bool operator !=(const mysql_type_info& a, const std::type_info& b)
00390 {
00391 return a.c_type() != b;
00392 }
00393
00394 }
00395
00396 #endif
00397