Index: trunk/sources/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/Importer/InfixExpressionParser.cs
===================================================================
--- trunk/sources/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/Importer/InfixExpressionParser.cs	(revision 14350)
+++ trunk/sources/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/Importer/InfixExpressionParser.cs	(revision 14826)
@@ -33,10 +33,26 @@
   /// Parses mathematical expressions in infix form. E.g. x1 * (3.0 * x2 + x3)
   /// Identifier format (functions or variables): '_' | letter { '_' | letter | digit }
-  /// Variables names can be set under quotes "" or '' because variable names might contain spaces. 
+  /// Variables names and variable values can be set under quotes "" or '' because variable names might contain spaces. 
+  ///   Variable = ident | " ident " | ' ident ' 
   /// It is also possible to use functions e.g. log("x1") or real-valued constants e.g. 3.1415 . 
   /// Variable names are case sensitive. Function names are not case sensitive.
+  /// 
+  /// 
+  /// S             = Expr EOF
+  /// Expr          = ['-' | '+'] Term { '+' Term | '-' Term }
+  /// Term          = Fact { '*' Fact | '/' Fact }
+  /// Fact          = '(' Expr ')' 
+  ///                 | 'LAG' '(' varId ',' ['+' | '-' ] number ')' 
+  ///                 | funcId '(' ArgList ')' 
+  ///                 | VarExpr | number
+  /// ArgList       = Expr { ',' Expr }
+  /// VarExpr       = varId OptFactorPart
+  /// OptFactorPart = [ ('=' varVal | '[' ['+' | '-' ] number {',' ['+' | '-' ] number } ']' ) ]
+  /// varId         =  ident | ' ident ' | " ident "
+  /// varVal        =  ident | ' ident ' | " ident "
+  /// ident         =  '_' | letter { '_' | letter | digit }
   /// </summary>
   public sealed class InfixExpressionParser {
-    private enum TokenType { Operator, Identifier, Number, LeftPar, RightPar, Comma, End, NA };
+    private enum TokenType { Operator, Identifier, Number, LeftPar, RightPar, LeftBracket, RightBracket, Comma, Eq, End, NA };
     private class Token {
       internal double doubleVal;
@@ -65,4 +81,6 @@
     private Constant constant = new Constant();
     private Variable variable = new Variable();
+    private BinaryFactorVariable binaryFactorVar = new BinaryFactorVariable();
+    private FactorVariable factorVar = new FactorVariable();
 
     private ProgramRootSymbol programRootSymbol = new ProgramRootSymbol();
@@ -150,4 +168,5 @@
             && str[pos] != '/'
             && str[pos] != ')'
+            && str[pos] != ']'
             && str[pos] != ',') {
             sb.Append(str[pos]);
@@ -214,4 +233,13 @@
           pos++;
           yield return new Token { TokenType = TokenType.RightPar, strVal = ")" };
+        } else if (str[pos] == '[') {
+          pos++;
+          yield return new Token { TokenType = TokenType.LeftBracket, strVal = "[" };
+        } else if (str[pos] == ']') {
+          pos++;
+          yield return new Token { TokenType = TokenType.RightBracket, strVal = "]" };
+        } else if (str[pos] == '=') {
+          pos++;
+          yield return new Token { TokenType = TokenType.Eq, strVal = "=" };
         } else if (str[pos] == ',') {
           pos++;
@@ -222,10 +250,5 @@
       }
     }
-
-    // S       = Expr EOF
-    // Expr    = ['-' | '+'] Term { '+' Term | '-' Term }
-    // Term    = Fact { '*' Fact | '/' Fact }
-    // Fact    = '(' Expr ')' | funcId '(' ArgList ')' | varId | number
-    // ArgList = Expr { ',' Expr }
+    /// S             = Expr EOF
     private ISymbolicExpressionTreeNode ParseS(Queue<Token> tokens) {
       var expr = ParseExpr(tokens);
@@ -237,4 +260,6 @@
       return expr;
     }
+
+    /// Expr          = ['-' | '+'] Term { '+' Term | '-' Term }
     private ISymbolicExpressionTreeNode ParseExpr(Queue<Token> tokens) {
       var next = tokens.Peek();
@@ -300,5 +325,5 @@
     }
 
-    // Term = Fact { '*' Fact | '/' Fact }
+    /// Term          = Fact { '*' Fact | '/' Fact }
     private ISymbolicExpressionTreeNode ParseTerm(Queue<Token> tokens) {
       var factors = new List<ISymbolicExpressionTreeNode>();
@@ -335,5 +360,14 @@
     }
 
-    // Fact = '(' Expr ')' | 'LAG' '(' varId ',' ['+' | '-'] number ')' | funcId '(' ArgList ')' | varId | number
+    /// Fact          = '(' Expr ')' 
+    ///                 | 'LAG' '(' varId ',' ['+' | '-' ] number ')' 
+    ///                 | funcId '(' ArgList ')' 
+    ///                 | VarExpr | number
+    /// ArgList       = Expr { ',' Expr }
+    /// VarExpr       = varId OptFactorPart
+    /// OptFactorPart = [ ('=' varVal | '[' ['+' | '-' ] number {',' ['+' | '-' ] number } ']' ) ]
+    /// varId         =  ident | ' ident ' | " ident "
+    /// varVal        =  ident | ' ident ' | " ident "
+    /// ident         =  '_' | letter { '_' | letter | digit }
     private ISymbolicExpressionTreeNode ParseFact(Queue<Token> tokens) {
       var next = tokens.Peek();
@@ -348,5 +382,5 @@
         var idTok = tokens.Dequeue();
         if (tokens.Peek().TokenType == TokenType.LeftPar) {
-          // function identifier
+          // function identifier or LAG
           var funcId = idTok.strVal.ToUpperInvariant();
 
@@ -394,8 +428,56 @@
         } else {
           // variable
-          var varNode = (VariableTreeNode)variable.CreateTreeNode();
-          varNode.Weight = 1.0;
-          varNode.VariableName = idTok.strVal;
-          return varNode;
+          if (tokens.Peek().TokenType == TokenType.Eq) {
+            // binary factor
+            tokens.Dequeue(); // skip Eq
+            var valTok = tokens.Dequeue();
+            if (valTok.TokenType != TokenType.Identifier) throw new ArgumentException("expected identifier");
+            var binFactorNode = (BinaryFactorVariableTreeNode)binaryFactorVar.CreateTreeNode();
+            binFactorNode.Weight = 1.0;
+            binFactorNode.VariableName = idTok.strVal;
+            binFactorNode.VariableValue = valTok.strVal;
+            return binFactorNode;
+          } else if (tokens.Peek().TokenType == TokenType.LeftBracket) {
+            // factor variable
+            var factorVariableNode = (FactorVariableTreeNode)factorVar.CreateTreeNode();
+            factorVariableNode.VariableName = idTok.strVal;
+
+            tokens.Dequeue(); // skip [
+            var weights = new List<double>();
+            // at least one weight is necessary
+            var sign = 1.0;
+            if (tokens.Peek().TokenType == TokenType.Operator) {
+              var opToken = tokens.Dequeue();
+              if (opToken.strVal == "+") sign = 1.0;
+              else if (opToken.strVal == "-") sign = -1.0;
+              else throw new ArgumentException();
+            }
+            if (tokens.Peek().TokenType != TokenType.Number) throw new ArgumentException("number expected");
+            var weightTok = tokens.Dequeue();
+            weights.Add(sign * weightTok.doubleVal);
+            while (tokens.Peek().TokenType == TokenType.Comma) {
+              // skip comma
+              tokens.Dequeue();
+              if (tokens.Peek().TokenType == TokenType.Operator) {
+                var opToken = tokens.Dequeue();
+                if (opToken.strVal == "+") sign = 1.0;
+                else if (opToken.strVal == "-") sign = -1.0;
+                else throw new ArgumentException();
+              }
+              weightTok = tokens.Dequeue();
+              if (weightTok.TokenType != TokenType.Number) throw new ArgumentException("number expected");
+              weights.Add(sign * weightTok.doubleVal);
+            }
+            var rightBracketToken = tokens.Dequeue();
+            if (rightBracketToken.TokenType != TokenType.RightBracket) throw new ArgumentException("closing bracket ] expected");
+            factorVariableNode.Weights = weights.ToArray();
+            return factorVariableNode;
+          } else {
+            // variable
+            var varNode = (VariableTreeNode)variable.CreateTreeNode();
+            varNode.Weight = 1.0;
+            varNode.VariableName = idTok.strVal;
+            return varNode;
+          }
         }
       } else if (next.TokenType == TokenType.Number) {
Index: trunk/sources/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/Importer/SymbolicExpressionImporter.cs
===================================================================
--- trunk/sources/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/Importer/SymbolicExpressionImporter.cs	(revision 14350)
+++ trunk/sources/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/Importer/SymbolicExpressionImporter.cs	(revision 14826)
@@ -35,5 +35,5 @@
     private const string INVOKESTART = "CALL";
     private const string TIMELAGSTART = "LAG";
-    private Dictionary<string, Symbol> knownSymbols = new Dictionary<string, Symbol>() 
+    private Dictionary<string, Symbol> knownSymbols = new Dictionary<string, Symbol>()
       {
         {"+", new Addition()},
@@ -45,4 +45,6 @@
         {"POW", new Power()},
         {"ROOT", new Root()},
+        {"SQR", new Square()},
+        {"SQRT", new SquareRoot()},
         {"SIN",new Sine()},
         {"COS", new Cosine()},
@@ -74,4 +76,6 @@
         {"PROG", new ProgramRootSymbol()},
         {"MAIN", new StartSymbol()},
+        {"FACTOR", new FactorVariable() },
+        {"BINFACTOR", new BinaryFactorVariable()}
       };
 
@@ -82,4 +86,6 @@
     TimeLag timeLag = new TimeLag();
     Integral integral = new Integral();
+    FactorVariable factorVar = new FactorVariable();
+    BinaryFactorVariable binFactorVar = new BinaryFactorVariable();
 
     ProgramRootSymbol programRootSymbol = new ProgramRootSymbol();
@@ -136,4 +142,8 @@
             tree.AddSubtree(ParseSexp(tokens));
           }
+        } else if (tokens.Peek().StringValue.StartsWith("FACTOR")) {
+          tree = ParseFactor(tokens);
+        } else if (tokens.Peek().StringValue.StartsWith("BINFACTOR")) {
+          tree = ParseBinaryFactor(tokens);
         } else {
           Token curToken = tokens.Dequeue();
@@ -201,4 +211,48 @@
     }
 
+    private ISymbolicExpressionTreeNode ParseFactor(Queue<Token> tokens) {
+      Token tok = tokens.Dequeue();
+      Debug.Assert(tok.StringValue == "FACTOR");
+      FactorVariableTreeNode t = (FactorVariableTreeNode)(new FactorVariable()).CreateTreeNode(); // create a new symbol each time on purpose
+      var varNameTok = tokens.Dequeue();
+      Debug.Assert(tok.Symbol == TokenSymbol.SYMB);
+      t.VariableName = varNameTok.StringValue;
+
+      var weights = new List<double>();
+      while (tokens.Peek().Symbol == TokenSymbol.NUMBER) {
+        weights.Add(tokens.Dequeue().DoubleValue);
+      }
+
+      t.Weights = weights.ToArray();
+
+      // create a set of (virtual) values to match the number of weights
+      t.Symbol.VariableNames = new string[] { t.VariableName };
+      t.Symbol.VariableValues = new[]
+      { new KeyValuePair<string, Dictionary<string,int>>(
+        t.VariableName,
+        weights.Select((_, i) => Tuple.Create(_,i)).ToDictionary(tup=>"X" + tup.Item2, tup=>tup.Item2)) };
+      return t;
+    }
+
+    private ISymbolicExpressionTreeNode ParseBinaryFactor(Queue<Token> tokens) {
+      Token tok = tokens.Dequeue();
+      Debug.Assert(tok.StringValue == "BINFACTOR");
+      var t = (BinaryFactorVariableTreeNode)binFactorVar.CreateTreeNode();
+      var varNameTok = tokens.Dequeue();
+      Debug.Assert(varNameTok.Symbol == TokenSymbol.SYMB);
+      t.VariableName = varNameTok.StringValue;
+
+      var varValTok = tokens.Dequeue();
+      Debug.Assert(varValTok.Symbol == TokenSymbol.SYMB);
+      t.VariableValue = varValTok.StringValue;
+
+      var weightTok = tokens.Dequeue();
+      Debug.Assert(weightTok.Symbol == TokenSymbol.NUMBER);
+      t.Weight = weightTok.DoubleValue;
+
+      return t;
+    }
+
+
     private ISymbolicExpressionTreeNode ParseLaggedVariable(Queue<Token> tokens) {
       Token varTok = tokens.Dequeue();
