• Main Page
  • Namespaces
  • Data Structures
  • Files
  • File List

/export/development/ViennaMath/viennamath/runtime/function_symbol.hpp

Go to the documentation of this file.
00001 #ifndef VIENNAMATH_RUNTIME_FUNCTION_SYMBOL_HPP
00002 #define VIENNAMATH_RUNTIME_FUNCTION_SYMBOL_HPP
00003 
00004 /* =======================================================================
00005    Copyright (c) 2012, Institute for Microelectronics,
00006                        Institute for Analysis and Scientific Computing,
00007                        TU Wien.
00008                              -----------------
00009                ViennaMath - Symbolic and Numerical Math in C++
00010                              -----------------
00011 
00012    Author:     Karl Rupp                          rupp@iue.tuwien.ac.at
00013 
00014    License:    MIT (X11), see file LICENSE in the ViennaMath base directory
00015 ======================================================================= */
00016 
00017 
00018 
00019 
00020 #include <ostream>
00021 #include <sstream>
00022 #include "viennamath/forwards.h"
00023 #include "viennamath/expression.hpp"
00024 #include "viennamath/compiletime/ct_function_symbol.hpp"
00025 #include "viennamath/runtime/expression_interface.hpp"
00026 
00031 namespace viennamath
00032 {
00033 
00038   template <typename InterfaceType>
00039   class rt_function_symbol : public InterfaceType
00040   {
00041       typedef rt_function_symbol<InterfaceType>     self_type;
00042     public:
00043       typedef typename InterfaceType::numeric_type      numeric_type;
00044       typedef InterfaceType                             interface_type;
00045       
00051       template <typename Tag>
00052       rt_function_symbol(id_type i, Tag const & t) : id_(i), tag_id_(Tag::tag_id()) {}
00053 
00059       rt_function_symbol(id_type i, id_type t = 0) : id_(i), tag_id_(t) {}
00060 
00061       rt_function_symbol() : id_(0), tag_id_(unknown_tag<>::tag_id()) {}
00062       
00063       id_type id() const { return id_; }
00064       id_type tag_id() const { return tag_id_; }
00065 
00066       //
00067       // interface requirements:
00068       //
00069       
00071       InterfaceType * clone() const { return new self_type(id_, tag_id_); }
00072       
00074       numeric_type eval(std::vector<double> const & v) const { throw expression_not_evaluable_exception("Cannot evaluate rt_function_symbol!"); return 0; }
00076       numeric_type eval(numeric_type v) const { throw expression_not_evaluable_exception("Cannot evaluate rt_function_symbol!"); return 0; }
00077       
00079       std::string deep_str() const
00080       {
00081         std::stringstream ss;
00082         ss << "function_symbol<";
00083         if (tag_id_ == unknown_tag<>::tag_id())
00084           ss << "unknown(" << id_ << ")>";
00085         else if (tag_id_ == test_tag<>::tag_id())
00086           ss << "test(" << id_ << ")>";
00087         else
00088           ss << "invalid>";
00089         
00090         return ss.str();      
00091       }
00092       
00094       numeric_type unwrap() const { throw expression_not_unwrappable_exception("Cannot evaluate rt_function_symbol to a number!"); }
00095       
00097       InterfaceType * substitute(const InterfaceType * e,
00098                                  const InterfaceType * repl) const
00099       {
00100         if (deep_equal(e))
00101             return repl->clone();
00102         
00103         return clone();
00104       };    
00105       
00107       InterfaceType * substitute(std::vector<const InterfaceType *> const &  e,
00108                                  std::vector<const InterfaceType *> const &  repl) const
00109       {
00110         //std::cout << "Comparing variable<" << id << "> with " << e->str() << ", result: ";
00111         for (std::size_t i=0; i<e.size(); ++i)
00112           if (deep_equal(e[i]))
00113             return repl[i]->clone();
00114         
00115         //std::cout << "FALSE" << std::endl;
00116         return clone();
00117       };    
00118       
00120       bool deep_equal(const InterfaceType * other) const
00121       {
00122         const self_type * ptr = dynamic_cast< const self_type *>(other);
00123         if (ptr != NULL)
00124           return (ptr->id() == id_ && ptr->tag_id_ == tag_id_);
00125 
00126         return false;
00127       }
00128       
00130       bool shallow_equal(const InterfaceType * other) const
00131       {
00132         return dynamic_cast< const self_type * >(other) != NULL;
00133       }
00134       
00136       InterfaceType * diff(const InterfaceType * diff_var) const
00137       {
00138         //this code should not be reached, because rt_function_symbol is symbolically differentiated at a higher level
00139         throw expression_not_differentiable_exception("Cannot differentiate rt_function_symbol!");
00140         return NULL;
00141       }
00142       
00143     private:
00145       id_type id_;
00147       id_type tag_id_;
00148   };
00149 
00150   
00151   
00152   template <typename InterfaceType>
00153   std::ostream& operator<<(std::ostream & stream, rt_function_symbol<InterfaceType> const & v)
00154   {
00155     stream << v.deep_str();
00156     return stream;
00157   }
00158   
00159   
00160   
00161 }
00162 
00163 #endif

Generated on Wed Feb 29 2012 21:50:43 for ViennaMath by  doxygen 1.7.1