title: How to add qi::symbols in grammar<Iterator,double()>?
body: <p>I am trying to use Boost.Spirit (V. 2.5) library to create a mini-calculator. Features I want to implement : 
  - basic calculus (+,-,/,*), that works
  - some functions (like min, max), that works too
  - declaring/assigning double variables, and there is the problem... when I add "[vars.add]" I get compilation error (template parameter ambiguious).
  I've tried "add(char_(_1)", "add(_1)",... and nothing seems to work. I am obviously missing something (not understanding something actually). If someone could help me on this I would me most gratefull!</p>
  
  <p>Here is the source :</p>
  
  <pre><code>#include &lt;boost/config/warning_disable.hpp&gt;
  #include &lt;boost/spirit/include/qi.hpp&gt;
  #include &lt;boost/spirit/include/phoenix_operator.hpp&gt;
  #include &lt;boost/spirit/home/phoenix/statement/if.hpp&gt;
  #include &lt;boost/spirit/home/phoenix/bind/bind_function.hpp&gt;
  
  #include &lt;iostream&gt;
  #include &lt;string&gt;
  
  namespace client
  {
      namespace qi = boost::spirit::qi;
      namespace ascii = boost::spirit::ascii;
      namespace phx = boost::phoenix;
  
      struct vars_ : qi::symbols&lt;char, double&gt; {
          vars_() {
              add("ans" , 0);
          }
      } vars;
  
      template &lt;typename Iterator&gt;
      struct parser : qi::grammar&lt;Iterator, double()&gt;
      {
          parser() : parser::base_type(function)
          {
              using qi::eps;
              using qi::lit;
              using qi::_val;
              using qi::_1;
              using ascii::char_;
              using qi::double_;
              using qi::string;
              using qi::lexeme;
              using boost::phoenix::if_;
              using qi::alpha;
              using qi::alnum;
  
              MAX = lexeme[string("max") | string("MAX")]; //define max symbol
  
              MIN = lexeme[string("min") | string("MIN")]; //define min symbol
  
              D   = lexeme[string("d") | string("D")];     //define distance symbol
  
              ANS = lexeme[string("ans") | string("ANS")]; //not working yet
  
              function =
                  expression                                      [_val = _1]
                  | declaration
                  | assignment
                  | ( MAX &gt;&gt; "(" &gt;&gt; function                      [_val = _1] &gt;&gt; 
                          +(',' &gt;&gt; function                       [if_(_1 &gt; _val)[_val = _1]]) &gt;&gt; ')') // call : max(function,...)
                  | ( MIN &gt;&gt; "(" &gt;&gt; function                      [_val = _1] &gt;&gt;
                          +(',' &gt;&gt; function                       [if_(_1 &lt; _val)[_val = _1]]) &gt;&gt; ')') // call : min(function,...)
                  | ( D   &gt;&gt; "(" &gt;&gt; (function &gt;&gt; ',' &gt;&gt; function) &gt;&gt; ')');                             // call : d(point1,point2) not implemented yet
  
              expression =
                  term                            [_val = _1]
                  &gt;&gt; *(   ('+' &gt;&gt; term            [_val += _1])
                      |   ('-' &gt;&gt; term            [_val -= _1]));
  
              term =
                  factor                          [_val = _1]
                  &gt;&gt; *(   ('*' &gt;&gt; factor          [_val *= _1])
                      |   ('/' &gt;&gt; factor          [_val /= _1]));
              factor = 
                  double_                         [_val = _1]
                  | (vars                         [_val += _1] )
                  |   '(' &gt;&gt; expression           [_val = _1] &gt;&gt; ')'
                  |   ('-' &gt;&gt; factor              [_val = -_1])
                  |   ('+' &gt;&gt; factor              [_val = _1])
                  | declaration;
              ;
  
              assignment =
                  vars &gt;&gt; '=' &gt;&gt; function;
  
              var_decl =
                  lexeme [ qi::raw [  ( alpha &gt;&gt; *( alnum | '_' ) ) - vars  ] ] //[ phx::bind(vars.add, _1) ]
                      ;
  
  
              declaration =
                  "var " &gt;&gt; var_decl &gt;&gt; *( ',' &gt;&gt; var_decl );
          }
  
          qi::rule&lt;Iterator, double()&gt; MAX, MIN, D, ANS, expression, term, factor, 
                                          function, assignment, var_decl, declaration;
      };
  }
  
  ///////////////////////////////////////////////////////////////////////////////
  //  Main program
  ///////////////////////////////////////////////////////////////////////////////
  int main()
  {
      std::cout &lt;&lt; "**********************************************************" &lt;&lt; std::endl;
      std::cout &lt;&lt; "*                                                        *" &lt;&lt; std::endl;
      std::cout &lt;&lt; "*          Command interface for VideoTraction4          *" &lt;&lt; std::endl;
      std::cout &lt;&lt; "*                                                        *" &lt;&lt; std::endl;
      std::cout &lt;&lt; "**********************************************************" &lt;&lt; std::endl &lt;&lt; std::endl;
      std::cout &lt;&lt; "Type an expression...or [q or Q] to quit" &lt;&lt; std::endl &lt;&lt; std::endl;
  
      typedef std::string::const_iterator iterator_type;
      typedef client::parser&lt;iterator_type&gt; parser;
  
      parser _parser; // Our grammar
  
      std::string str;
      double result;
      while (std::getline(std::cin, str))
      {
          if (str.empty() || str[0] == 'q' || str[0] == 'Q')
              break;
  
          std::string::const_iterator iter = str.begin();
          std::string::const_iterator end = str.end();
  
          bool r = parse(iter, end, _parser, result);
  
          if (r &amp;&amp; iter == end)
          {
              std::cout &lt;&lt; "-------------------------\n";
              std::cout &lt;&lt; "Parsing succeeded\n";
              std::cout &lt;&lt; "result = " &lt;&lt; result &lt;&lt; std::endl;
              std::cout &lt;&lt; "-------------------------\n";
              client::vars.remove("ans");
              client::vars.add("ans",result);
          }
          else
          {
              std::string rest(iter, end);
              std::cout &lt;&lt; "-------------------------\n";
              std::cout &lt;&lt; "Parsing failed\n";
              std::cout &lt;&lt; "stopped at: \": " &lt;&lt; rest &lt;&lt; "\"\n";
              std::cout &lt;&lt; "-------------------------\n";
          }
      }
  
      std::cout &lt;&lt; "Bye... :-) \n\n";
      return 0;
  }
  </code></pre>
  
  <p>I would like to do things such as :</p>
  
  <pre><code>var i,j
  i = 1
  j = max(2*(i+1),5)
  </code></pre>