formula_function.hpp

Go to the documentation of this file.
00001 
00002 /* $Id: formula_function.hpp 52533 2012-01-07 02:35:17Z shadowmaster $ */
00003 /*
00004    Copyright (C) 2008 - 2012 by David White <dave@whitevine.net>
00005    Part of the Battle for Wesnoth Project http://www.wesnoth.org/
00006 
00007    This program is free software; you can redistribute it and/or modify
00008    it under the terms of the GNU General Public License as published by
00009    the Free Software Foundation; either version 2 of the License, or
00010    (at your option) any later version.
00011    This program is distributed in the hope that it will be useful,
00012    but WITHOUT ANY WARRANTY.
00013 
00014    See the COPYING file for more details.
00015 */
00016 
00017 #ifndef FORMULA_FUNCTION_HPP_INCLUDED
00018 #define FORMULA_FUNCTION_HPP_INCLUDED
00019 
00020 #include "formula.hpp"
00021 #include "formula_callable.hpp"
00022 
00023 namespace game_logic {
00024 
00025 class formula_expression {
00026 public:
00027     formula_expression() : name_("") {}
00028     virtual ~formula_expression() {}
00029     variant evaluate(const formula_callable& variables, formula_debugger *fdb = NULL) const {
00030         call_stack_manager manager(name_);
00031         if (fdb!=NULL) {
00032             return evaluate_arg_callback(*fdb,*this,variables);
00033         } else {
00034             return execute(variables,fdb);
00035         }
00036     }
00037     void set_name(const char* name) { name_ = name; }
00038 
00039     const char* get_name() const { return name_; }
00040     virtual std::string str() const = 0;
00041 private:
00042     virtual variant execute(const formula_callable& variables, formula_debugger *fdb = NULL) const = 0;
00043     const char* name_;
00044         friend class formula_debugger;
00045 };
00046 
00047 typedef boost::shared_ptr<formula_expression> expression_ptr;
00048 
00049 class function_expression : public formula_expression {
00050 public:
00051     typedef std::vector<expression_ptr> args_list;
00052     explicit function_expression(
00053                         const std::string& name,
00054                         const args_list& args,
00055                         int min_args=-1, int max_args=-1)
00056         : name_(name), args_(args)
00057     {
00058         set_name(name.c_str());
00059         if(min_args >= 0 && args_.size() < static_cast<size_t>(min_args)) {
00060             throw formula_error("Too few arguments", "", "", 0);
00061         }
00062 
00063         if(max_args >= 0 && args_.size() > static_cast<size_t>(max_args)) {
00064             throw formula_error("Too many arguments", "", "", 0);
00065         }
00066     }
00067     virtual std::string str() const;
00068 protected:
00069     const args_list& args() const { return args_; }
00070 private:
00071     std::string name_;
00072     args_list args_;
00073 };
00074 
00075 class key_value_pair : public formula_callable {
00076     variant key_;
00077     variant value_;
00078 
00079     variant get_value(const std::string& key) const;
00080 
00081     void get_inputs(std::vector<game_logic::formula_input>* inputs) const;
00082 public:
00083     explicit key_value_pair(const variant& key, const variant& value) : key_(key), value_(value) {}
00084 };
00085 
00086 class formula_function_expression : public function_expression {
00087 public:
00088     explicit formula_function_expression(const std::string& name, const args_list& args, const_formula_ptr formula, const_formula_ptr precondition, const std::vector<std::string>& arg_names);
00089 private:
00090     variant execute(const formula_callable& variables, formula_debugger *fdb) const;
00091     const_formula_ptr formula_;
00092     const_formula_ptr precondition_;
00093     std::vector<std::string> arg_names_;
00094     int star_arg_;
00095 };
00096 
00097 typedef boost::shared_ptr<function_expression> function_expression_ptr;
00098 
00099 class formula_function {
00100     std::string name_;
00101     const_formula_ptr formula_;
00102     const_formula_ptr precondition_;
00103     std::vector<std::string> args_;
00104 public:
00105     formula_function() :
00106         name_(),
00107         formula_(),
00108         precondition_(),
00109         args_()
00110     {
00111     }
00112 
00113     formula_function(const std::string& name, const_formula_ptr formula, const_formula_ptr precondition, const std::vector<std::string>& args) : name_(name), formula_(formula), precondition_(precondition), args_(args)
00114     {}
00115 
00116     function_expression_ptr generate_function_expression(const std::vector<expression_ptr>& args) const;
00117 };
00118 
00119 class function_symbol_table {
00120     std::map<std::string, formula_function> custom_formulas_;
00121 public:
00122     function_symbol_table() :
00123         custom_formulas_()
00124     {
00125     }
00126 
00127     virtual ~function_symbol_table() {}
00128     virtual void add_formula_function(const std::string& name, const_formula_ptr formula, const_formula_ptr precondition, const std::vector<std::string>& args);
00129     virtual expression_ptr create_function(const std::string& fn,
00130                                            const std::vector<expression_ptr>& args) const;
00131     std::vector<std::string> get_function_names() const;
00132 };
00133 
00134 expression_ptr create_function(const std::string& fn,
00135                                const std::vector<expression_ptr>& args,
00136                                const function_symbol_table* symbols);
00137 std::vector<std::string> builtin_function_names();
00138 
00139 
00140 class wrapper_formula : public formula_expression {
00141 public:
00142     wrapper_formula()
00143         : arg_()
00144     {
00145     }
00146 
00147     wrapper_formula(expression_ptr arg)
00148         : arg_(arg)
00149     {
00150     }
00151 
00152     virtual ~wrapper_formula()
00153     {
00154     }
00155 
00156     virtual std::string str() const
00157     {
00158         if (arg_) {
00159             return arg_->str();
00160         } else {
00161             return "";
00162         }
00163     }
00164 private:
00165     virtual variant execute(const formula_callable& variables, formula_debugger *fdb = NULL) const
00166     {
00167         if (arg_) {
00168             return arg_->evaluate(variables,fdb);
00169         } else {
00170             return variant();
00171         }
00172     }
00173     expression_ptr arg_;
00174 };
00175 
00176 }
00177 
00178 #endif
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines

Generated by doxygen 1.7.1 on Fri May 25 2012 01:02:51 for The Battle for Wesnoth
Gna! | Forum | Wiki | CIA | devdocs