basix_doc 0.1
/Users/mourrain/Devel/mmx/basix/include/basix/generic.hpp
Go to the documentation of this file.
00001 
00002 /******************************************************************************
00003 * MODULE     : generic.hpp
00004 * DESCRIPTION: Generic expressions
00005 * COPYRIGHT  : (C) 2005  Joris van der Hoeven
00006 *******************************************************************************
00007 * This software falls under the GNU general public license and comes WITHOUT
00008 * ANY WARRANTY WHATSOEVER. See the file $TEXMACS_PATH/LICENSE for more details.
00009 * If you don't have this file, write to the Free Software Foundation, Inc.,
00010 * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
00011 ******************************************************************************/
00012 
00013 #ifndef __GENERIC_HPP
00014 #define __GENERIC_HPP
00015 #include <typeinfo>
00016 #include <basix/defaults.hpp>
00017 
00019 
00020 namespace mmx {
00021 #define TMPL template<typename C>
00022 #define Acc accelerator<C>
00023 class generic;
00024 class syntactic;
00025 class port;
00026 class string;
00027 class routine;
00028 class routine_rep;
00029 struct exact_eq_table;
00030 template<typename T,typename F> struct as_helper;
00031 template<typename T,typename F> inline T as (const F& x);
00032 template<typename C> struct vector_as_helper;
00033 TMPL struct inspector;
00034 TMPL struct binary_helper;
00035 generic gen_vec ();
00036 generic gen_vec (const generic& g1);
00037 generic gen_vec (const generic& g1, const generic& g2);
00038 generic gen_vec (const generic& g1, const generic& g2, const generic& g3);
00039 generic vector_access (const generic& g, nat i);
00040 TMPL generic binary_disassemble (const C& x);
00041 TMPL void binary_write (const port& out, const C& x);
00042 TMPL inline port operator << (const port& out, const C& x);
00043 void write (const port& p, const char* s, nat n);
00044 void write (const port& p, const string& s);
00045 extern port mmout;
00046 extern port mmerr;
00047 extern bool booting_done;
00048 extern generic GEN_CONVERT;
00049 
00050 /******************************************************************************
00051 * Accelerated methods
00052 ******************************************************************************/
00053 
00054 #define ACC_NEGATE          0
00055 #define ACC_SQUARE          1
00056 #define ACC_INVERT          2
00057 #define ACC_ADD             3
00058 #define ACC_SUB             4
00059 #define ACC_MUL             5
00060 #define ACC_DIV             6
00061 #define ACC_SQRT            8
00062 #define ACC_EXP             9
00063 #define ACC_LOG            10
00064 #define ACC_COS            11
00065 #define ACC_SIN            12
00066 #define ACC_TAN            13
00067 #define ACC_ACOS           14
00068 #define ACC_ASIN           15
00069 #define ACC_ATAN           16
00070 #define ACC_COSH           17
00071 #define ACC_SINH           18
00072 #define ACC_TANH           19
00073 #define ACC_ACOSH          20
00074 #define ACC_ASINH          21
00075 #define ACC_ATANH          22
00076 #define ACC_HYPOT          23
00077 #define ACC_ATAN2          24
00078 #define ACC_POW            25
00079 #define ACC_LESS           26
00080 #define ACC_LESSEQ         27
00081 #define ACC_GTR            28
00082 #define ACC_GTREQ          29
00083 #define ACC_DERIVE         30
00084 #define ACC_DERIVE_WRT     31
00085 #define ACC_INTEGRATE      32
00086 #define ACC_INTEGRATE_WRT  33
00087 
00088 /******************************************************************************
00089 * The generic class
00090 ******************************************************************************/
00091 
00092 class generic_rep: public rep_struct {
00093 public:
00094   virtual nat get_type () const = 0;
00095   virtual bool same_type (const generic& g) const = 0;
00096   virtual nat get_symbolic_type () const = 0;
00097   virtual nat get_species_type () const = 0;
00098   virtual nat get_length () const = 0;
00099   virtual generic get_child (nat i) const = 0;
00100   virtual nat get_hard_hash_value () const = 0;
00101   virtual nat get_exact_hash_value () const = 0;
00102   virtual nat get_hash_value () const = 0;
00103   virtual bool is_hard_eq (const generic& rep) const = 0;
00104   virtual bool is_exact_eq (const generic& rep) const = 0;
00105   virtual bool is_equal (const generic& rep) const = 0;
00106   virtual generic duplicate_me () const = 0;
00107   virtual syntactic expression () const = 0;
00108   virtual generic binary_type () const = 0;
00109   virtual generic binary_disassemble () const = 0;
00110   virtual void binary_write (const port& p) const = 0;
00111   virtual generic make_abstract_vector () const = 0;
00112   virtual generic make_concrete_vector (const generic& v) const = 0;
00113 
00114   virtual nat      acc_id () const;
00115   virtual routine* acc_construct (nat id) const;
00116   virtual routine* acc_apply (nat code) const;
00117 
00118 public:
00119   inline generic_rep () {}
00120   inline virtual ~generic_rep () {}
00121   inline generic me () const;
00122 
00123   friend class generic;
00124 };
00125   
00126 class generic {
00127 INDIRECT_PROTO (generic, generic_rep)
00128 public:
00129   generic ();
00130   generic (const char* s);
00131   generic (const string& s);
00132   generic (int i);
00133   generic (nat i);
00134   generic operator () () const;
00135   generic operator () (const generic& g1) const;
00136   generic operator () (const generic& g1, const generic& g2) const;
00137   generic operator () (const generic& g1, const generic& g2,
00138                        const generic& g3) const;
00139 
00140   inline generic operator [] (nat i) const { return rep->get_child (i); }
00141   inline friend generic_rep* inspect (const generic& g) { return g.rep; };
00142   friend syntactic flatten (const generic& g);
00143 
00144   friend class generic_rep;
00145 };
00146 INDIRECT_IMPL (generic, generic_rep)
00147 
00148 inline generic generic_rep::me () const {
00149   return generic (this, true); }
00150 inline nat type (const generic& g) {
00151   return g->get_type (); }
00152 inline nat symbolic_type (const generic& g) {
00153   return g->get_symbolic_type (); }
00154 inline nat species_type (const generic& g) {
00155   return g->get_species_type (); }
00156 inline nat N (const generic& g) {
00157   return g->get_length (); }
00158 inline nat gen_hash (const generic& g) {
00159   return g->get_hard_hash_value (); }
00160 inline nat exact_hash (const generic& g) {
00161   return g->get_exact_hash_value (); }
00162 inline nat hash (const generic& g) {
00163   return g->get_hash_value (); }
00164 inline bool gen_eq (const generic& g1, const generic& g2) {
00165   return g1->is_hard_eq (g2); }
00166 inline bool gen_neq (const generic& g1, const generic& g2) {
00167   return !g1->is_hard_eq (g2); }
00168 
00169 /******************************************************************************
00170 * Type information
00171 ******************************************************************************/
00172 
00173 nat new_type_id ();
00174 nat new_type_id (const char*);
00175 
00176 template<typename T>
00177 inline nat global_type_id () { return new_type_id (typeid (T ()).name()); }  
00178 inline nat binary_id (nat id1, nat id2) { return id1 ^ (0x10115 * id2); }
00179 template<typename T> struct type_information { static nat id; };
00180 template<typename T> nat type_information<T>::id= global_type_id<T> ();
00181 STMPL struct type_information<generic> { static nat id; };
00182 TMPL inline bool is (const generic& x) {
00183   return type (x) == type_information<C>::id; }
00184 inline bool same_type (const generic& x1, const generic& x2) {
00185   return x1->same_type (x2); }
00186 vector<generic> all_type_names ();
00187 void define_type_sub (const generic& name, nat id);
00188 nat type_id (const generic& name);
00189 generic type_name (nat id);
00190 generic type_name (const generic& g);
00191 template<typename C> inline nat type_id () {
00192   return type_information<C>::id; }
00193 template<typename C> inline generic type_name () {
00194   return type_name (type_id<C> ()); }
00195 
00196 #define SYMBOLIC_UNSPECIFIED  0
00197 #define SYMBOLIC_INTEGER      1
00198 #define SYMBOLIC_RATIONAL     2
00199 #define SYMBOLIC_FLOATING     3
00200 #define SYMBOLIC_BALL         4
00201 #define SYMBOLIC_REAL         5
00202 #define SYMBOLIC_LITERAL      6
00203 #define SYMBOLIC_COMPOUND     7
00204 #define SYMBOLIC_SUM          8
00205 #define SYMBOLIC_PRODUCT      9
00206 #define SYMBOLIC_DERIVATIVE  10
00207 #define SYMBOLIC_FUNCTION    11
00208 
00209 template<typename T> struct symbolic_type_information {
00210   static const nat id= SYMBOLIC_UNSPECIFIED; };
00211 
00212 #define SPECIES_DEFAULT   0
00213 #define SPECIES_VECTOR    1
00214 #define SPECIES_LIST      2
00215 #define SPECIES_TABLE     3
00216 
00217 template<typename T> struct species_type_information {
00218   static const nat id= SPECIES_DEFAULT; };
00219 inline bool is_vector (const generic& x) {
00220   return species_type (x) == SPECIES_VECTOR; }
00221 inline bool is_list (const generic& x) {
00222   return species_type (x) == SPECIES_LIST; }
00223 inline bool is_table (const generic& x) {
00224   return species_type (x) == SPECIES_TABLE; }
00225 
00226 /******************************************************************************
00227 * Syntactic manipulation of generic objects
00228 ******************************************************************************/
00229 
00230 generic lit (const char* s);
00231 generic lit (const string& s);
00232 
00233 generic gen (const generic& x1, const vector<generic>& v);
00234 generic gen ();
00235 generic gen (const generic& x1);
00236 generic gen (const generic& x1, const string& x2);
00237 generic gen (const generic& x1, const generic& x2);
00238 generic gen (const generic& x1, const generic& x2, const generic& x3);
00239 generic gen (const generic& x1, const generic& x2,
00240              const generic& x3, const generic& x4);
00241 generic gen (const generic& x1, const generic& x2,
00242              const generic& x3, const generic& x4, const generic& x5);
00243 generic gen (const generic& x1, const generic& x2,
00244              const generic& x3, const generic& x4,
00245              const generic& x5, const generic& x6);
00246 
00247 generic void_value ();
00248 generic comma ();
00249 generic comma (const generic& x1, const generic& x2);
00250 generic xgen (const generic& f, const generic& args);
00251 generic xaccess (const generic& f, const generic& args);
00252 generic xtuple (const generic& args);
00253 generic xsqtuple (const generic& args);
00254 generic xrow (const generic& args);
00255 generic access (const generic& f, const generic& x);
00256 generic access (const generic& f, const generic& x, const generic& y);
00257 generic access (const generic& f, const vector<generic>& x);
00258 
00259 generic as_object (const generic& v, nat tp_id);
00260 generic as_object (const generic& v, const generic& tp);
00261 generic as_generic (const generic& obj, nat tp_id);
00262 generic as_generic (const generic& obj, const generic& tp);
00263 
00264 generic range (const generic& g, nat start, nat end);
00265 generic append (const generic& g1, const generic& g2);
00266 generic cons (const generic& g1, const generic& g2);
00267 generic cons (const generic& g1, const generic& g2, const generic& g3);
00268 generic car (const generic& g);
00269 generic cdr (const generic& g);
00270 
00271 bool is_func (const generic& g, const char* f);
00272 bool is_func (const generic& g, const char* f, nat n);
00273 bool is_func (const generic& g, const generic& f);
00274 bool is_func (const generic& g, const generic& f, nat n);
00275 nat size (const generic& g);
00276 int big_small_compare (const generic& g1, const generic& g2);
00277 int small_big_compare (const generic& g1, const generic& g2);
00278 
00279 /******************************************************************************
00280 * Generic functions
00281 ******************************************************************************/
00282 
00283 generic convert (const generic& from, const generic& to);
00284 
00285 void set_smallest (generic& x);
00286 void set_largest (generic& x);
00287 void set_accuracy (generic& x);
00288 void set_pi (generic& x);
00289 void set_log2 (generic& x);
00290 void set_euler (generic& x);
00291 void set_catalan (generic& x);
00292 void set_imaginary (generic& x);
00293 void set_nan (generic& x);
00294 void set_fuzz (generic& x);
00295 void set_infinity (generic& x);
00296 void set_maximal (generic& x);
00297 void set_minimal (generic& x);
00298 
00299 generic operator - (const generic& x1);
00300 generic square (const generic &x1);
00301 generic invert (const generic &x1);
00302 generic operator + (const generic& x1, const generic& x2);
00303 generic operator - (const generic& x1, const generic& x2);
00304 generic operator * (const generic& x1, const generic& x2);
00305 generic operator / (const generic& x1, const generic& x2);
00306 generic operator + (const generic& x1, const int& x2);
00307 generic operator - (const generic& x1, const int& x2);
00308 generic operator * (const generic& x1, const int& x2);
00309 generic operator / (const generic& x1, const int& x2);
00310 generic operator + (const int& x1, const generic& x2);
00311 generic operator - (const int& x1, const generic& x2);
00312 generic operator * (const int& x1, const generic& x2);
00313 generic operator / (const int& x1, const generic& x2);
00314 
00315 generic sqrt (const generic& x1);
00316 generic exp (const generic& x1);
00317 generic log (const generic& x1);
00318 generic cos (const generic& x1);
00319 generic sin (const generic& x1);
00320 generic tan (const generic& x1);
00321 generic acos (const generic& x1);
00322 generic asin (const generic& x1);
00323 generic atan (const generic& x1);
00324 generic cosh (const generic& x1);
00325 generic sinh (const generic& x1);
00326 generic tanh (const generic& x1);
00327 generic acosh (const generic& x1);
00328 generic asinh (const generic& x1);
00329 generic atanh (const generic& x1);
00330 generic hypot (const generic& x1, const generic& x2);
00331 generic atan2 (const generic& x1, const generic& x2);
00332 generic pow (const generic& x1, const generic& x2);
00333 generic pow (const generic& x1, const int& x2);
00334 generic pow (const int& x1, const generic& x2);
00335 
00336 bool operator == (const generic& x1, const generic& x2);
00337 bool operator != (const generic& x1, const generic& x2);
00338 bool operator == (const generic& x1, const int& x2);
00339 bool operator != (const generic& x1, const int& x2);
00340 bool operator == (const int& x1, const generic& x2);
00341 bool operator != (const int& x1, const generic& x2);
00342 bool exact_eq  (const generic& x1, const generic& x2);
00343 bool exact_neq (const generic& x1, const generic& x2);
00344 bool exact_eq  (const generic& x1, const int& x2);
00345 bool exact_neq (const generic& x1, const int& x2);
00346 bool exact_eq  (const int& x1, const generic& x2);
00347 bool exact_neq (const int& x1, const generic& x2);
00348 inline bool is_exact_zero (const generic& g1) { return exact_eq (g1, 0); }
00349 
00350 bool operator < (const generic& x1, const generic& x2);
00351 bool operator <= (const generic& x1, const generic& x2);
00352 bool operator > (const generic& x1, const generic& x2);
00353 bool operator >= (const generic& x1, const generic& x2);
00354 bool operator < (const generic& x1, const int& x2);
00355 bool operator <= (const generic& x1, const int& x2);
00356 bool operator > (const generic& x1, const int& x2);
00357 bool operator >= (const generic& x1, const int& x2);
00358 bool operator < (const int& x1, const generic& x2);
00359 bool operator <= (const int& x1, const generic& x2);
00360 bool operator > (const int& x1, const generic& x2);
00361 bool operator >= (const int& x1, const generic& x2);
00362 
00363 generic derive (const generic& x1);
00364 generic integrate (const generic& x1);
00365 generic derive (const generic& x1, const generic& x2);
00366 generic integrate (const generic& x1, const generic& x2);
00367 
00368 /******************************************************************************
00369 * Routines based on the current evaluator
00370 ******************************************************************************/
00371 
00372 generic construct (const int& i);
00373 generic construct (const nat& i);
00374 generic construct (const double& x);
00375 generic construct (const float& x);
00376 generic construct (const generic& x);
00377 generic eval (const generic& x);
00378 
00379 generic apply (const generic& f, const generic& x);
00380 generic apply (const generic& f, const generic& x, const generic& y);
00381 generic apply (const generic& f, const generic& x,
00382                const generic& y, const generic& z);
00383 generic apply (const generic& f, const vector<generic>& x);
00384 
00385 generic quo (const generic& x1, const generic& x2);
00386 generic rem (const generic& x1, const generic& x2);
00387 generic numerator (const generic& x);
00388 generic denominator (const generic& x);
00389 generic gcd (const generic& x1, const generic& x2);
00390 generic lcm (const generic& x1, const generic& x2);
00391 TMPL struct xgcd_matrix;
00392 xgcd_matrix<generic> xgcd (const generic& x1, const generic& x2);
00393 
00394 generic pow (const generic& x1, const nat& x2);
00395 generic pow (const nat& x1, const generic& x2);
00396 generic trig (const generic& x1);
00397 
00398 generic min (const generic& x1, const generic& x2);
00399 generic max (const generic& x1, const generic& x2);
00400 generic abs (const generic& x1);
00401 generic arg (const generic& x1);
00402 generic Re (const generic& x1);
00403 generic Im (const generic& x1);
00404 generic conj (const generic& x1);
00405 generic gaussian (const generic& x1, const generic& x2);
00406 generic polar (const generic& x1, const generic& x2);
00407 
00408 generic floor (const generic& x);
00409 generic trunc (const generic& x);
00410 generic ceil (const generic& x);
00411 generic round (const generic& x);
00412 
00413 generic prime (const generic& x1);
00414 generic substitute (const generic& x1, const generic& x2);
00415 generic compose (const generic& x1, const generic& x2);
00416 generic dilate (const generic& x1, const generic& x2);
00417 generic solve (const generic& x1, const generic& x2);
00418 
00419 generic sqrt_init (const generic& x, const generic& c);
00420 generic log_init (const generic& x, const generic& c);
00421 generic acos_init (const generic& x, const generic& c);
00422 generic asin_init (const generic& x, const generic& c);
00423 generic atan_init (const generic& x, const generic& c);
00424 generic integrate_init (const generic& x, const generic& c);
00425 generic solve_lde_init (const generic& x, const generic& c);
00426 
00427 generic change_precision (const generic& x, xnat p);
00428 xnat    precision (const generic& x);
00429 generic next_above (const generic& x);
00430 generic next_below (const generic& x);
00431 generic rounding_error (const generic& x);
00432 generic additive_error (const generic& x);
00433 generic multiplicative_error (const generic& x);
00434 generic elementary_error (const generic& x);
00435 xint    exponent (const generic& x);
00436 double  magnitude (const generic& x);
00437 generic incexp2 (const generic& x1, const xint& x2);
00438 generic decexp2 (const generic& x1, const xint& x2);
00439 generic operator << (const generic& x1, const generic& x2);
00440 generic operator >> (const generic& x1, const generic& x2);
00441 
00442 generic lshiftz (const generic& x1, const generic& x2);
00443 generic rshiftz (const generic& x1, const generic& x2);
00444 generic operator | (const generic& x1, const generic& x2);
00445 generic operator & (const generic& x1, const generic& x2);
00446 generic lres (const generic& x1, const generic& x2);
00447 generic rres (const generic& x1, const generic& x2);
00448 generic uniform (const generic& x1, const generic& x2);
00449 generic specialize (const generic& x1, const generic& x2);
00450 
00451 generic center (const generic& x1);
00452 generic radius (const generic& x1);
00453 generic sharpen (const generic& x1);
00454 generic blur (const generic& x1, const generic& x2);
00455 
00456 /******************************************************************************
00457 * Accelerators
00458 ******************************************************************************/
00459 
00460 TMPL
00461 struct accelerator {
00462   static nat id;
00463   static routine *construct;
00464   static nat nr_construct;
00465   static routine *apply;
00466   static nat nr_apply;
00467   static void set_construct (nat id, const routine& r);
00468   static void set_apply (nat code, const routine& r);
00469 };
00470 
00471 TMPL nat Acc::id= (nat) -1;
00472 TMPL routine *Acc::construct= NULL;
00473 TMPL nat Acc::nr_construct= (nat) 0;
00474 TMPL routine *Acc::apply= NULL;
00475 TMPL nat Acc::nr_apply= (nat) 0;
00476 
00477 typedef routine* vec_routine;
00478 void fill_out (vec_routine& v, nat& n, nat i, const routine& r);
00479 
00480 /******************************************************************************
00481 * Concrete instances
00482 ******************************************************************************/
00483 
00484 TMPL
00485 class generic_concrete_rep: public generic_rep {
00486 public:
00487   C rep;
00488 
00489 protected:
00490   nat get_type () const { return type_information<C>::id; }
00491   bool same_type (const generic& g) const { return is<C> (g); }
00492   nat get_symbolic_type () const { return symbolic_type_information<C>::id; }
00493   nat get_species_type () const { return species_type_information<C>::id; }
00494   nat get_length () const { return inspector<C>::length (rep); }
00495   generic get_child (nat i) const { return inspector<C>::access (rep, i); }
00496   nat get_hard_hash_value () const { return hard_hash (rep); }
00497   nat get_exact_hash_value () const { return exact_hash (rep); }
00498   nat get_hash_value () const { return hash (rep); }
00499   bool is_hard_eq (const generic& g) const {
00500     if (type (g) != type_information<C>::id) return false;
00501     return hard_eq (rep, ((generic_concrete_rep<C>*) inspect (g)) -> rep); }
00502   bool is_exact_eq (const generic& g) const {
00503     if (type (g) != type_information<C>::id) return false;
00504     return exact_eq (rep, ((generic_concrete_rep<C>*) inspect (g)) -> rep); }
00505   bool is_equal (const generic& g) const {
00506     if (type (g) != type_information<C>::id) return false;
00507     return rep == ((generic_concrete_rep<C>*) inspect (g)) -> rep; }
00508   generic duplicate_me () const { return as<generic> (duplicate (rep)); }
00509   syntactic expression () const; // definition in syntactic.hpp
00510   generic binary_type () const {
00511     return binary_helper<C>::full_type_name (); }
00512   generic binary_disassemble () const {
00513     return mmx::binary_disassemble (rep); }
00514   void binary_write (const port& out) const {
00515     mmx::write (out, binary_helper<C>::short_type_name ());
00516     mmx::write (out, ":", 1);
00517     mmx::binary_write (out, rep); }
00518   generic make_abstract_vector () const {
00519     return vector_as_helper<C>::abstract (rep); }
00520   generic make_concrete_vector (const generic& v) const {
00521     return as<generic> (vector_as_helper<C>::concrete (v)); }
00522 
00523   inline nat acc_id () const {
00524     return Acc::id; }
00525   inline routine* acc_construct (nat id) const {
00526     if (id < Acc::nr_construct)
00527       return (routine*) (void*)
00528         (((routine_rep**) (void*) Acc::construct) + id);
00529     else return NULL; }
00530   inline routine* acc_apply (nat code) const {
00531     if (code < Acc::nr_apply)
00532       return (routine*) (void*)
00533         (((routine_rep**) (void*) Acc::apply) + code);
00534     else return NULL; }
00535 
00536 public:
00537   generic_concrete_rep (const C& rep2): rep (rep2) {}
00538 };
00539 
00540 TMPL
00541 struct as_helper<generic,C> {
00542   static inline generic cv (const C& x) {
00543     return new generic_concrete_rep<C> (x); }
00544 };
00545 
00546 TMPL
00547 struct as_helper<C,generic> {
00548   static inline C cv (const generic& x) {
00549     return ((generic_concrete_rep<C>*) inspect(x)) -> rep; }
00550 };
00551 
00552 STMPL
00553 struct as_helper<generic,generic> {
00554   static inline generic cv (const generic& x) { return x; }
00555 };
00556 
00557 TMPL generic
00558 as_generic (const C& c) {
00559   return construct (new generic_concrete_rep<C> (c));
00560 }
00561 
00562 TMPL inline void
00563 set_as (generic& r, const C& x) {
00564   r= new generic_concrete_rep<C> (x);
00565 }
00566 
00567 TMPL inline void
00568 set_as (C& r, const generic& x) {
00569   r= ((generic_concrete_rep<C>*) inspect(x)) -> rep;
00570 }
00571 
00572 inline void
00573 set_as (generic& r, const generic& x) {
00574  r= x;
00575 }
00576 
00577 #undef TMPL
00578 #undef Acc
00579 } // namespace mmx
00580 #endif // __GENERIC_HPP
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines