Массовое обновление запроса Linq to Nhibernate? - PullRequest
3 голосов
/ 22 января 2010

Не уверен, что я что-то здесь упускаю. В основном, я ищу Linq для Nhibernate, чтобы сделать следующий оператор SQL:

update SomeTable
set SomeInteger = (SomeInteger + 1)
where SomeInteger > @NotSoMagicNumber

Есть ли способ сделать это?

Спасибо!

Ответы [ 3 ]

3 голосов
/ 01 ноября 2017

Поздний ответ, но теперь он существует в Nhibernate 5.0.

    //
    // Summary:
    //     Update all entities selected by the specified query. The update operation is
    //     performed in the database without reading the entities out of it.
    //
    // Parameters:
    //   source:
    //     The query matching the entities to update.
    //
    //   expression:
    //     The update setters expressed as a member initialization of updated entities,
    //     e.g. x => new Dog { Name = x.Name, Age = x.Age + 5 }. Unset members are ignored
    //     and left untouched.
    //
    // Type parameters:
    //   TSource:
    //     The type of the elements of source.
    //
    // Returns:
    //     The number of updated entities.
    public static int Update<TSource>(this IQueryable<TSource> source, Expression<Func<TSource, TSource>> expression);

В вашем случае:

    session.Query<SomeObject>()
            .Update(i => new SomeObject { SomeInteger = i.SomeInteger + 1 });

Спасибо команде NHibernate!

1 голос
/ 05 февраля 2010

Linq (не Linq для NHibernate, Linq в целом) не имеет глагола массового обновления, как SQL. Если вам нужна эффективность массового обновления, как у вас, я бы просто придерживался SQL.

1 голос
/ 30 января 2010

Как и большинство (если не все) провайдеров LINQ, LINQ to NHibernate полезна только для чтения данных.

Чтобы достичь того, что вы хотите сделать в NHibernate с помощью LINQ, вам нужно получить все соответствующие объекты и обновить каждый. Что-то вроде:

//NHibernate session initialisation & finalisation skipped for brevity

var relevantObjects = from i in session.Linq<SomeObject>()
                      where i.SomeInteger > notSoMagicNumber
                      select i;

foreach (SomeObject item in relevantObjects)
{
    i.SomeInteger++;
    session.Update(item);
}

Убедитесь, что вы очистили свой сеанс после всего этого и завернули все в транзакцию, чтобы минимизировать количество обновлений базы данных.

Все это говорит о том, что в зависимости от размера ваших данных вы можете столкнуться с проблемами производительности при использовании NHibernate для массовых операций. Использование IStatelessSession может помочь для этой цели, но я сам не пробовал.

ОБНОВЛЕНИЕ Оказывается, если вы завершили его в транзакции, вам не нужно делать session.Update или очищать сеанс.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...