Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/linq/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
如何在动态LINQ中使用动态Lambda_Linq_Dynamic_Lambda - Fatal编程技术网

如何在动态LINQ中使用动态Lambda

如何在动态LINQ中使用动态Lambda,linq,dynamic,lambda,Linq,Dynamic,Lambda,在搜索表达式解析器时,我找到了。我想使用这个API让最终用户为业务对象的验证指定一些标准 因此,我第一次尝试使用该库成功地进行了以下单元测试 var x = Expression.Parameter(typeof(int), "x"); var list = Expression.Parameter(typeof(List<int>), "list"); var e = DynamicExpression.ParseLambda(new[] { x, list }, null, "l

在搜索表达式解析器时,我找到了。我想使用这个API让最终用户为业务对象的验证指定一些标准

因此,我第一次尝试使用该库成功地进行了以下单元测试

var x = Expression.Parameter(typeof(int), "x");
var list = Expression.Parameter(typeof(List<int>), "list");
var e = DynamicExpression.ParseLambda(new[] { x, list }, null, "list.Any(it == x)");
var compiledExpression = e.Compile();

var myList = new List<int> { 24, 46, 67, 78 };
Assert.AreEqual(false, compiledExpression.DynamicInvoke(2, myList));
Assert.AreEqual(true, compiledExpression.DynamicInvoke(24, myList));
进入

然而,第二种语法允许我嵌套lambda(这是我的最终目标),如下所示:


有人知道如何调整Dynamic.cs以支持这种语法吗?

经过几个小时的调试,我自己找到了解决方案

以下单元测试现在成功:

var list1 = Expression.Parameter(typeof(List<int>), "list1");
var list2 = Expression.Parameter(typeof(List<int>), "list2");
var e = DynamicExpression.ParseLambda(new[] { list1, list2 }, null, "list2.All(i => list1.Any(j => j == i))");
var compiledExpression = e.Compile();

var myList1 = new List<int> { 24, 46, 67, 78 };
var myList2 = new List<int> { 46 };
var myList3 = new List<int> { 8 };
Assert.AreEqual(true, compiledExpression.DynamicInvoke(myList1, myList2));
Assert.AreEqual(false, compiledExpression.DynamicInvoke(myList1, myList3));

4) 更换(从第1151行开始)

5) 更换(从第1838行开始)


您是否尝试过单独构建lambda并将嵌套的lambda作为参数传递?我还没试过,但我的这些改变也值得一试。需要与您描述的类似的功能。谢谢,这帮我省去了几个小时的痛苦。
list.Any(i => i == x) // Raises error: No property or field 'i' exists in type 'int'
list1.All(i => list2.Any(j => j == i))
var list1 = Expression.Parameter(typeof(List<int>), "list1");
var list2 = Expression.Parameter(typeof(List<int>), "list2");
var e = DynamicExpression.ParseLambda(new[] { list1, list2 }, null, "list2.All(i => list1.Any(j => j == i))");
var compiledExpression = e.Compile();

var myList1 = new List<int> { 24, 46, 67, 78 };
var myList2 = new List<int> { 46 };
var myList3 = new List<int> { 8 };
Assert.AreEqual(true, compiledExpression.DynamicInvoke(myList1, myList2));
Assert.AreEqual(false, compiledExpression.DynamicInvoke(myList1, myList3));
if (symbols.TryGetValue(token.text, out value) ||
    externals != null && externals.TryGetValue(token.text, out value)) {
if (symbols.TryGetValue(token.text, out value) ||
externals != null && externals.TryGetValue(token.text, out value) ||
internals.TryGetValue(token.text, out value)) {
if (member == null)
    throw ParseError(errorPos, Res.UnknownPropertyOrField,
       id, GetTypeName(type));
if (member == null)
{
    if(token.id == TokenId.Lambda && it.Type == type)
    {
        // This might be an internal variable for use within a lambda expression, so store it as such
        internals.Add(id, it);
        NextToken();
        var right = ParseExpression();
        return right;
    }
    else
    {
        throw ParseError(errorPos, Res.UnknownPropertyOrField,
            id, GetTypeName(type));                        
    }
}
case '=':
NextChar();
if (ch == '=') {
    NextChar();
    t = TokenId.DoubleEqual;
}
else {
    t = TokenId.Equal;
}
break;
case '=':
NextChar();
if (ch == '=') {
    NextChar();
    t = TokenId.DoubleEqual;
}
else if(ch == '>')
{
    NextChar();
    t = TokenId.Lambda;
}
else {
    t = TokenId.Equal;
}
break;