Использование PredicateBuilder с VB.NET

Я воссоздал класс Predicatebuilder в отдельном проекте C # и пытаюсь использовать его в проекте VB.NET, но все равно получаю следующую ошибку:

Не удалось разрешить перегрузку, поскольку доступное «ИЛИ» не принимает такое количество аргументов.

когда использую вот так:

Dim predicate = PredicateBuilder.False(Of t_Quote)()
predicate = predicate.Or(Function(q) q.iQuoteType = iQuoteType)

Имеется ссылка на соответствующий проект, я использую правильный оператор импорта, и все это компилируется без каких-либо ошибок.

Есть идеи, где я ошибаюсь?

Вот класс PredicateBuilder на C #, который я использую:

публичный статический класс PredicateBuilder {публичное статическое выражение> True () {return f => true; } публичное статическое выражение> False () {return f => false; }

    public static Expression<Func<T, bool>> Or<T>(this

Выражение> expr1, Выражение> expr2) {var invokedExpr = Expression.Invoke (expr2, expr1.Parameters.Cast ()); return Expression.Lambda> (Expression.OrElse (expr1.Body, invokedExpr), expr1.Parameters); }

    public static Expression<Func<T, bool>> And<T>(this

Выражение> expr1, Выражение> expr2) {var invokedExpr = Expression.Invoke (expr2, expr1.Parameters.Cast ()); return Expression.Lambda> (Expression.AndAlso (expr1.Body, invokedExpr), expr1.Parameters); }}


person rollercoast    schedule 01.10.2009    source источник
comment
Не зная собственного API, невозможно дать ответ на этот вопрос. Опубликуйте версию кода C # или отправьте подпись в метод PredicateBuilder.Or.   -  person Juliet    schedule 02.10.2009


Ответы (4)


Вот код, который у меня работает в VB.NET, так как я также настроил этот класс для работы в VB.NET ...

Imports System.Linq.Expressions

Public Module PredicateBuilder
    Public Function [True](Of T)() As Expression(Of Func(Of T, Boolean))
        Return Function(f) True
    End Function

    Public Function [False](Of T)() As Expression(Of Func(Of T, Boolean))
        Return Function(f) False
    End Function

    <System.Runtime.CompilerServices.Extension()> _
    Public Function [Or](Of T)(ByVal expr1 As Expression(Of Func(Of T, Boolean)), ByVal expr2 As Expression(Of Func(Of T, Boolean))) As Expression(Of Func(Of T, Boolean))
        Dim invokedExpr = Expression.Invoke(expr2, expr1.Parameters.Cast(Of Expression)())
        Return Expression.Lambda(Of Func(Of T, Boolean))(Expression.[Or](expr1.Body, invokedExpr), expr1.Parameters)
    End Function

    <System.Runtime.CompilerServices.Extension()> _
    Public Function [And](Of T)(ByVal expr1 As Expression(Of Func(Of T, Boolean)), ByVal expr2 As Expression(Of Func(Of T, Boolean))) As Expression(Of Func(Of T, Boolean))
        Dim invokedExpr = Expression.Invoke(expr2, expr1.Parameters.Cast(Of Expression)())
        Return Expression.Lambda(Of Func(Of T, Boolean))(Expression.[And](expr1.Body, invokedExpr), expr1.Parameters)
    End Function
End Module

И вот как я его использую:

Dim pred = PredicateBuilder.True(Of MyClass)()

pred = pred.And(Function(m As MyClass) m.SomeProperty = someValue)
pred = pred.Or(Function(m As MyClass) m.SomeProperty = someValue)
person Brandon    schedule 01.10.2009

Решил вопрос. Это произошло из-за того, что Option Infer был отключен. Как только я установил для него значение «Вкл», был получен правильный тип, и все заработало, как должно.

person rollercoast    schedule 02.10.2009
comment
Убедитесь, что вы установили это как принятый ответ, так как это полезная информация для других! - person Mike Hofer; 02.10.2009

Одна вещь, о которой следует помнить, хотя это может не решить вашу конкретную проблему, - это чувствительность к регистру при работе с межъязыковыми решениями.

C # и сама среда CLR чувствительны к регистру; VB.NET - нет. В зависимости от того, каким образом вы используете библиотеку, может возникнуть исключение, потому что регистр не соответствует (и, следовательно, не может быть разрешен до известного типа).

Это может произойти, если вы считаете, что последовательно объявляете имена пространств имен, но в одном классе пространство имен объявлено с одним символом в верхнем регистре. Это очень легко сделать в Visual Basic, но для VB.NET все они выглядят так, как будто они скомпилированы в единое связное пространство имен. Что касается CLR, то это два разных пространства имен.

Я сталкивался с этой проблемой раньше, и это была очень неуловимая ошибка, которую нужно было отследить.

Я знаю, что вы используете проект C # из VB.NET, но следите за проблемами такого типа.

person Mike Hofer    schedule 02.10.2009

Меня устраивает:

Dim predicate = PredicateBuilder.False(Of Integer)()
predicate = predicate.Or(Function(q) q Mod 2 = 0)

(У меня нет твоего t_Quote типа)

Кроме того, это ужасная практика - иметь такое имя типа, как t_Quote. Это должно называться Quote; Венгерская нотация и символы подчеркивания не одобряются в именах C #.

person SLaks    schedule 01.10.2009
comment
Я принимаю ваш комментарий относительно соглашения об именах (не мой выбор!). Тип t_Quote - это класс linq to sql, помогает ли эта информация в решении этой проблемы? - person rollercoast; 02.10.2009