00001
00002
00003 #include "cppscript"
00004 #include "dynamic/extensions.hpp"
00005 #include "wrap_cpp_container.hpp"
00006
00007 #include <cstdlib>
00008
00009
00010 static_call( register_pickle_type( cmp_string, "" ) );
00011 static_call( register_pickle_type( cmp_wstring, L"" ) );
00012
00013
00014 namespace
00015 {
00016 typedef std::basic_string<char, std::char_traits<char>, dynamic::allocator<char> > narrow_string;
00017
00018 typedef std::basic_string<wchar_t, std::char_traits<wchar_t>, dynamic::allocator<wchar_t> > wide_string;
00019
00020 template<typename Char> struct string_traits2;
00021
00022
00023 template<> struct string_traits2<char>
00024 {
00025 static std::string as_string(const var & v)
00026 {
00027 return v.as_string();
00028 }
00029
00030 static const var_cmp_index comparison_index = cmp_string;
00031 };
00032
00033
00034 template<> struct string_traits2<wchar_t>
00035 {
00036 static const var_cmp_index comparison_index = cmp_wstring;
00037
00038 static dynamic::wstring as_string(const var & v)
00039 {
00040 return v.as_wstring();
00041 }
00042 };
00043
00044
00045 template<typename Char>
00046 struct string_traits
00047 {
00048 typedef Char char_type;
00049
00050 typedef Char value_type;
00051
00052 typedef std::basic_string<Char> std_string;
00053
00054 typedef std::basic_string<Char, std::char_traits<Char>, dynamic::allocator<Char> > container;
00055
00056 static var key(int i)
00057 {
00058 return i;
00059 }
00060
00061 static var value(Char i)
00062 {
00063 return i;
00064 }
00065
00066 static var deref(Char i)
00067 {
00068 return i;
00069 }
00070
00071 static void mark_reachable(int i, gc::garbage_collector & gc)
00072 {
00073 }
00074
00075 static const var_cmp_index comparison_index = string_traits2<Char>::comparison_index;
00076
00077 static char pad_value()
00078 {
00079 return ' ';
00080 }
00081
00082 static char to_value(const var & v)
00083 {
00084 return v.as_int();
00085 }
00086
00087 static var back(const container & c)
00088 {
00089 return c[c.size()-1];
00090 }
00091
00092 static void pop_back(container & c)
00093 {
00094 c.resize(c.size()-1);
00095 }
00096
00097 static var front(const container & c)
00098 {
00099 return c[0];
00100 }
00101
00102 static void pickle(pickler & p, int ch)
00103 {
00104 p.write_int(ch);
00105 }
00106
00107 static char_type unpickle(unpickler & u)
00108 {
00109 return u.read_int();
00110 }
00111
00112 static std_string as_string(const var & s)
00113 {
00114 return string_traits2<Char>::as_string(s);
00115 }
00116
00117 static const char * class_name()
00118 {
00119 return "string";
00120 }
00121
00122 static const char * iterator_class_name()
00123 {
00124 return "string::iterator";
00125 }
00126 };
00127 }
00128
00129 namespace dynamic
00130 {
00131 namespace types
00132 {
00133
00135
00136 template<typename Impl>
00137 class string_impl : public internal::wrap_vector_container<Impl>
00138 {
00139 public:
00140 string_impl(const typename Impl::char_type * s)
00141 {
00142 this->m_data = s;
00143 }
00144
00145 string_impl(const typename Impl::container & s)
00146 {
00147 this->m_data = s;
00148 }
00149
00150 template<typename Ch, typename Traits, typename Alloc>
00151 string_impl(const std::basic_string<Ch, Traits, Alloc> & s)
00152 {
00153 this->m_data.assign(s.begin(), s.end());
00154 }
00155
00156 void short_output(ostream & os)
00157 {
00158 output(os);
00159 }
00160
00161 void short_output(wostream & os)
00162 {
00163 output(os);
00164 }
00165
00166 void output(ostream & os)
00167 {
00168 for(typename Impl::container::const_iterator i=this->m_data.begin();
00169 i!=this->m_data.end();
00170 ++i)
00171 {
00172 os << char(*i);
00173 }
00174 }
00175
00176 var clone()
00177 {
00178 return new string_impl(*this);
00179 }
00180
00181 void output(wostream & os)
00182 {
00183 for(typename Impl::container::const_iterator i=this->m_data.begin();
00184 i!=this->m_data.end();
00185 ++i)
00186 {
00187 os << wchar_t(*i);
00188 }
00189 }
00190
00191 static int to_int(const narrow_string & str)
00192 {
00193 return atoi(str.c_str());
00194 }
00195
00196 static int to_int(const wide_string & str)
00197 {
00199 return atoi(std::string(str.begin(), str.end()).c_str());
00200 }
00201
00202 static double to_double(const narrow_string & str)
00203 {
00204 return atof(str.c_str());
00205 }
00206
00207 static double to_double(const wide_string & str)
00208 {
00210 return atof(std::string(str.begin(), str.end()).c_str());
00211 }
00212
00213 int as_int()
00214 {
00216 return to_int(this->m_data);
00217 }
00218
00219 double as_double()
00220 {
00222 return to_double(this->m_data);
00223 }
00224
00225 var op_add(const var & s)
00226 {
00227 return this->m_data.c_str() + Impl::as_string(s);
00228 }
00229
00230 var op_mul(const var & v)
00231 {
00232 typename Impl::std_string result;
00233 int n = v.as_int();
00234 result.reserve(n * this->m_data.size());
00235 for(int i=0; i<n; ++i)
00236 result.append(this->m_data.begin(), this->m_data.end());
00237 return result;
00238 }
00239
00240 void assign_add(const var & v)
00241 {
00242 std::string v_str = v.as_string();
00243 this->m_data.append(v_str.begin(), v_str.end());
00244 }
00245
00246 var_cmp_result compare2(const var & other)
00247 {
00248 string_impl * other_string = dynamic_cast<string_impl*>(other.impl().shared_var());
00249
00250 if(!other_string) return cmp_not_equal;
00251
00252 return this->m_data < other_string->m_data ? cmp_lt : this->m_data > other_string->m_data ? cmp_gt : cmp_equal;
00253 }
00254 };
00255 }
00256 }
00257
00258
00259 var dynamic::internal::create_string(const char * str)
00260 {
00261 return str ? new types::string_impl<string_traits<char> >(str) : var();
00262 }
00263
00264 var dynamic::internal::create_string(const std::string & str)
00265 {
00266 return new types::string_impl<string_traits<char> >(str);
00267 }
00268
00269 var dynamic::internal::create_string(const wchar_t * str)
00270 {
00271 return str ? new types::string_impl<string_traits<wchar_t> >(str) : var();
00272 }
00273
00274 var dynamic::internal::create_string(const wstring & str)
00275 {
00276 return new types::string_impl<string_traits<wchar_t> >(str);
00277 }
00278
00279 var dynamic::string_from(const var & a)
00280 {
00281 var result="";
00282 foreach(i, a) result.push_back(i);
00283 return result;
00284 }
00285