/// <summary>
        /// Reads a lambda expression.
        /// </summary>
        /// <param name="parentReference">The parent code unit.</param>
        /// <param name="unsafeCode">Indicates whether the code being parsed resides in an unsafe code block.</param>
        /// <returns>Returns the expression.</returns>
        private LambdaExpression GetLambdaExpression(Reference<ICodePart> parentReference, bool unsafeCode)
        {
            Param.AssertNotNull(parentReference, "parentReference");
            Param.Ignore(unsafeCode);

            // Create an empty lambda expression.
            var lambdaExpression = new LambdaExpression();
            var expressionReference = new Reference<ICodePart>();

            // Check whether the next symbol is an opening parenthesis.
            Symbol symbol = this.GetNextSymbol(parentReference);

            Node<CsToken> previousTokenNode = this.tokens.Last;
            ICollection<Parameter> parameters = null;

            if (symbol.SymbolType == SymbolType.OpenParenthesis)
            {
                parameters = this.ParseAnonymousMethodParameterList(expressionReference, unsafeCode);
            }
            else
            {
                // Since the statement did not begin with an opening parenthesis,
                // it must begin with a single unknown symbol.
                if (symbol.SymbolType != SymbolType.Other)
                {
                    throw new SyntaxException(this.document.SourceCode, symbol.LineNumber);
                }

                CsToken token = this.GetToken(CsTokenType.Other, SymbolType.Other, expressionReference);
                this.tokens.Add(token);

                // Add the single parameter.
                lambdaExpression.AddParameter(new Parameter(
                    null,
                    token.Text,
                    expressionReference,
                    ParameterModifiers.None,
                    null,
                    token.Location,
                    new CsTokenList(this.tokens, this.tokens.Last, this.tokens.Last),
                    token.Generated));
            }

            // Get the lambda operator.
            this.tokens.Add(this.GetOperatorToken(OperatorType.Lambda, expressionReference));

            // Get the body of the expression. This can either be an expression or a statement.
            // If it starts with an opening curly bracket, it's a statement, otherwise it's an expression.
            symbol = this.GetNextSymbol(expressionReference);

            if (symbol.SymbolType == SymbolType.OpenCurlyBracket)
            {
                lambdaExpression.AnonymousFunctionBody = this.GetNextStatement(expressionReference, unsafeCode);
            }
            else
            {
                lambdaExpression.AnonymousFunctionBody = this.GetNextExpression(ExpressionPrecedence.None, expressionReference, unsafeCode);
            }

            // Create the overall token list for the expression.
            Node<CsToken> firstNode = previousTokenNode == null ? this.tokens.First : previousTokenNode.Next;
            lambdaExpression.Tokens = new CsTokenList(this.tokens, firstNode, this.tokens.Last);

            // Get the item's argument list if necessary.
            if (parameters != null && parameters.Count > 0)
            {
                lambdaExpression.AddParameters(parameters);
            }

            // Add a variable for each of the parameters.
            if (lambdaExpression.Parameters != null && lambdaExpression.Parameters.Count > 0)
            {
                // Add a variable for each of the parameters.
                foreach (Parameter parameter in lambdaExpression.Parameters)
                {
                    lambdaExpression.Variables.Add(new Variable(
                        parameter.Type,
                        parameter.Name,
                        VariableModifiers.None,
                        parameter.Location,
                        expressionReference,
                        parameter.Generated));
                }
            }

            // Return the expression.
            expressionReference.Target = lambdaExpression;
            return lambdaExpression;
        }
Пример #2
0
 private LambdaExpression GetLambdaExpression(bool unsafeCode)
 {
     LambdaExpression expression = new LambdaExpression();
     Symbol nextSymbol = this.GetNextSymbol();
     Microsoft.StyleCop.Node<CsToken> last = this.tokens.Last;
     ICollection<Parameter> items = null;
     if (nextSymbol.SymbolType == SymbolType.OpenParenthesis)
     {
         items = this.ParseAnonymousMethodParameterList(unsafeCode);
     }
     else
     {
         if (nextSymbol.SymbolType != SymbolType.Other)
         {
             throw new SyntaxException(this.document.SourceCode, nextSymbol.LineNumber);
         }
         CsToken item = this.GetToken(CsTokenType.Other, SymbolType.Other);
         this.tokens.Add(item);
         expression.AddParameter(new Parameter(null, item.Text, ParameterModifiers.None, item.Location, new CsTokenList(this.tokens, this.tokens.Last, this.tokens.Last), item.Generated));
     }
     this.tokens.Add(this.GetOperatorToken(OperatorType.Lambda));
     if (this.GetNextSymbol().SymbolType == SymbolType.OpenCurlyBracket)
     {
         expression.AnonymousFunctionBody = this.GetNextStatement(unsafeCode);
     }
     else
     {
         expression.AnonymousFunctionBody = this.GetNextExpression(ExpressionPrecedence.None, unsafeCode);
     }
     Microsoft.StyleCop.Node<CsToken> firstItemNode = (last == null) ? this.tokens.First : last.Next;
     expression.Tokens = new CsTokenList(this.tokens, firstItemNode, this.tokens.Last);
     if ((items != null) && (items.Count > 0))
     {
         expression.AddParameters(items);
     }
     if ((expression.Parameters != null) && (expression.Parameters.Count > 0))
     {
         foreach (Parameter parameter in expression.Parameters)
         {
             expression.Variables.Add(new Variable(parameter.Type, parameter.Name, VariableModifiers.None, parameter.Location.StartPoint, parameter.Generated));
         }
     }
     return expression;
 }