SQL(sp + view || Linq)
От: divergo  
Дата: 06.03.11 17:47
Оценка:
Навеяно опросом
Автор: Shmj
Дата: 06.03.11
Вопрос: Язык SQL не очень удобен для написания логики. Но иногда полезно писать основную логику приложения в триггерах и хранимых процедурах для сокращения передаваемых данных (между базой и приложением). Как вы решаете данную проблему?
и рабочей ситуацией.

Есть задача перевода на Linq приложения построенного на основе датасетов, хранимых процедур и представлений.
При этом присутствуют громоздкие запросы в коде в виде строк собранных конкатенацией.
Проще всего было бы их вынести в хранимки, но... мы же используем Linq!

Ну не вижу я никаких достоинств в написании сколько-нибудь сложных запросов на Linq.
Зачем?, SQL привычен, хранимки быстрее, меньше шансов написать неоптимальный запрос.

В чем суть этой "панацеи от всех бед"?
Re: SQL(sp + view || Linq)
От: Lloyd Россия  
Дата: 06.03.11 17:50
Оценка:
Здравствуйте, divergo, Вы писали:

D>Ну не вижу я никаких достоинств в написании сколько-нибудь сложных запросов на Linq.

D>Зачем?,

Типизированности недостаточно?

D>SQL привычен,


Будет linq привычен

D>хранимки быстрее,


Не быстрее

D>меньше шансов написать неоптимальный запрос.


Больше шансов написать неоптимальный код
Re: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 06.03.11 18:47
Оценка: 12 (1)
Здравствуйте, divergo, Вы писали:

D>Ну не вижу я никаких достоинств в написании сколько-нибудь сложных запросов на Linq.


Вместо конкатенации строк в Linq можно использовать составление запросов из отдельных выражений. Для написания действительно сложных запросов в Linq можно использовать повторное использование кода, в SQL это несколько затруднено. Не забываем так же про ассоциации, которые позволяют избавиться от ручного выпиливания джоинов.

D>Зачем?, SQL привычен, хранимки быстрее, меньше шансов написать неоптимальный запрос.


Хранимки быстрее — это анахронизм.

D>В чем суть этой "панацеи от всех бед"?


Главным образом в типизации. Как следствие, рефакторинг базы данных превращается в такое же по сложности занятие, как обычный рефакторинг кода.
Если нам не помогут, то мы тоже никого не пощадим.
Re[2]: SQL(sp + view || Linq)
От: Alexander Polyakov  
Дата: 08.03.11 19:59
Оценка: :)
Здравствуйте, IT, Вы писали:

IT>Вместо конкатенации строк в Linq можно использовать составление запросов из отдельных выражений.

Это приемлемо работает в ограниченной области, склейка строк гораздо мощнее. Ты (и никто другой) так не привел решения вот для этого примера
Автор: Alexander Polyakov
Дата: 02.11.10
(схему базы я запостил).
Re[3]: SQL(sp + view || Linq)
От: LeonidV Ниоткуда http://vygovskiy.com
Дата: 08.03.11 20:18
Оценка:
Здравствуйте, Alexander Polyakov, Вы писали:

AP>Здравствуйте, IT, Вы писали:


IT>>Вместо конкатенации строк в Linq можно использовать составление запросов из отдельных выражений.

AP>Это приемлемо работает в ограниченной области, склейка строк гораздо мощнее. Ты (и никто другой) так не привел решения вот для этого примера
Автор: Alexander Polyakov
Дата: 02.11.10
(схему базы я запостил).

Да вообще-то я привел...
http://jvmmemory.com — простой способ настройки JVM
Re[3]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 08.03.11 20:40
Оценка: +1
Здравствуйте, Alexander Polyakov, Вы писали:

IT>>Вместо конкатенации строк в Linq можно использовать составление запросов из отдельных выражений.

AP>Это приемлемо работает в ограниченной области, склейка строк гораздо мощнее. Ты (и никто другой) так не привел решения вот для этого примера
Автор: Alexander Polyakov
Дата: 02.11.10
(схему базы я запостил).


Немного мощнее, но и на два порядка глюкавее. Как правило базы, для которых написан такой код уже большне никогда серьёзно не рефакторятся. Само понятие "рефакторинг БД" для таких приложений представляется только как жуткий кошмар. Рефакторинг базы, для которой клиенты написаны на Linq вполне нормально рефакторятся.

Что касается твоего примера, то детально разбираться с ним в частности и с твоей задачей в целом нет ни желания, ни времени. Могу только сказать, что мы у себя генерируем Expression Tree по данным, находящимся в БД, что означает, что никаких особых проблем с генерацией ET нет. Но нужно учитывать, что общее решение для подобной задачи может вылиться в нечто весьма трудоёмкое, в то время как частные решения могут быть довольно просты. Ты искал общее решение для своего класса задач как способ подтвердить или опровергнуть возможность Linq решать такие задачи. Простого общего решения нет, частное тебя не интересует. Ну тут я
Если нам не помогут, то мы тоже никого не пощадим.
Re[4]: SQL(sp + view || Linq)
От: Alexander Polyakov  
Дата: 09.03.11 21:21
Оценка:
Здравствуйте, IT, Вы писали:

IT>Что касается твоего примера, то детально разбираться с ним в частности и с твоей задачей в целом нет ни желания, ни времени.

Тут
Автор: IT
Дата: 03.11.10
ты писал несколько иначе:

А вот со вторым EXISTS (точнее с генерацией вложенного SELECT) действительно не всё так просто. Надо подумать, может как-то можно решить и эту проблему.

По прошествии 4-х месяцев ты так и не придумал решение. Слив засчитан.
Re[5]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 09.03.11 21:28
Оценка: :)
Здравствуйте, Alexander Polyakov, Вы писали:

AP>По прошествии 4-х месяцев ты так и не придумал решение.


Я и не думал.

AP>Слив засчитан.


Если нам не помогут, то мы тоже никого не пощадим.
Re[2]: SQL(sp + view || Linq)
От: Кондор Россия  
Дата: 12.03.11 11:23
Оценка:
Здравствуйте, IT, Вы писали:
IT>Хранимки быстрее — это анахронизм.
Почему не быстрее? они ведь кешируются. Плюс как выяснять с linq какая часть кода провисает. В случае с хранимками
запускаем профайлер и видим что хранимка выполняется n секунд. переписываем ее и видим уже m секунд. Как подобный процесс выглядит с linq?
ДДТ!
Re[3]: SQL(sp + view || Linq)
От: Lloyd Россия  
Дата: 12.03.11 11:30
Оценка:
Здравствуйте, Кондор, Вы писали:

IT>>Хранимки быстрее — это анахронизм.

К>Почему не быстрее? они ведь кешируются.

Кешируются не хранимки, а планы sql-запросов, независимо от того, откуда взялся этот запрос — пришел из хранимки или с клиента.

К>Плюс как выяснять с linq какая часть кода провисает. В случае с хранимками

К>запускаем профайлер и видим что хранимка выполняется n секунд. переписываем ее и видим уже m секунд. Как подобный процесс выглядит с linq?

Таким же образом. Только в отличие от хранимок у нас есть полноценные профайлеры, которые могут показать, какой код сколько времени выполнялся.
Re[4]: SQL(sp + view || Linq)
От: denisio_mcp  
Дата: 12.03.11 12:32
Оценка: +1
Здравствуйте, Lloyd, Вы писали:

К>>Плюс как выяснять с linq какая часть кода провисает. В случае с хранимками

К>>запускаем профайлер и видим что хранимка выполняется n секунд. переписываем ее и видим уже m секунд. Как подобный процесс выглядит с linq?

L>Таким же образом. Только в отличие от хранимок у нас есть полноценные профайлеры, которые могут показать, какой код сколько времени выполнялся.


Вот только в случае с хранимкой ты получаешь чистое SQL-выражение которое можешь оптимизировать, а в случае Linq — у тебя добавляется ещё и ORM. И хинты не пропишешь. Сложные выражения надо бы выносить в хранимки и также из Linq дергать.
... << RSDN@Home 1.2.0 alpha 4 rev. 1476>>
Re[5]: SQL(sp + view || Linq)
От: Lloyd Россия  
Дата: 12.03.11 19:19
Оценка: +1
Здравствуйте, denisio_mcp, Вы писали:

L>>Таким же образом. Только в отличие от хранимок у нас есть полноценные профайлеры, которые могут показать, какой код сколько времени выполнялся.


_>Вот только в случае с хранимкой ты получаешь чистое SQL-выражение которое можешь оптимизировать, а в случае Linq — у тебя добавляется ещё и ORM. И хинты не пропишешь. Сложные выражения надо бы выносить в хранимки и также из Linq дергать.


Да, так и есть. Но сложные выражения — это дай бог 10% случаев, их не грех и руками переписать.
Re[5]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 12.03.11 20:06
Оценка: +1
Здравствуйте, denisio_mcp, Вы писали:

_>Вот только в случае с хранимкой ты получаешь чистое SQL-выражение которое можешь оптимизировать, а в случае Linq — у тебя добавляется ещё и ORM. И хинты не пропишешь.


Это недостаток не Linq в целом, а лишь конкретных реализаций Linq-провайдеров.

_>Сложные выражения надо бы выносить в хранимки и также из Linq дергать.


Не всё так просто. SQL не имеет нормальных средств повторного использования кода, не позволяет вводить абстракции, отличается полным отсутствием типизации. В результате, сложный код в хранимках — это прежде всего тормоз развития всего приложения. Нужно очень сильно не любить людей, чтобы заталкивать основную логику приложения в хранимки.

Из опыта пользователей того же BLToolkit переписывание хранимок на Linq запросы позволяло увеличивать производительность запросов на порядок (хотя тут разница видимо в мозгах, а не в linq/stored procs). В общем, утверждение о крутости хранимок сегодня в 2011-м году весьма спорно.
Если нам не помогут, то мы тоже никого не пощадим.
Re[6]: SQL(sp + view || Linq)
От: -VaS- Россия vaskir.blogspot.com
Дата: 26.03.11 09:34
Оценка:
IT>Нужно очень сильно не любить людей, чтобы заталкивать основную логику приложения в хранимки.

Не для всех типов приложений это так. Когда эта самая "основная логика" должна оперировать десятками и сотнями миллионов строк, то линки с хибернейтами дружно отправляются в сад.
Re[7]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 26.03.11 14:12
Оценка: +1
Здравствуйте, -VaS-, Вы писали:

IT>>Нужно очень сильно не любить людей, чтобы заталкивать основную логику приложения в хранимки.

VS>Не для всех типов приложений это так. Когда эта самая "основная логика" должна оперировать десятками и сотнями миллионов строк, то линки с хибернейтами дружно отправляются в сад.

Вообще-то, Linq вполне можно использовать как генерилку SQL и все сотни миллионов строк совсем не обязательно вытаскивать на клиента, если ты об этом.
Если нам не помогут, то мы тоже никого не пощадим.
Re: SQL(sp + view || Linq)
От: rm822 Россия  
Дата: 28.03.11 21:33
Оценка:
D>Ну не вижу я никаких достоинств в написании сколько-нибудь сложных запросов на Linq.
вы не одиноки

D>В чем суть этой "панацеи от всех бед"?

ИМХО в 2х вещах
-очень удобно аспнетчикам с их стейтлесс моделью
-это что-то типа визарда\кодгенератора: пока данных мало и нагрузка мала — сойдет и так
... << RSDN@Home 1.1.4 stable SR1 rev. 568>>
Re: SQL(sp + view || Linq)
От: adontz Грузия http://adontz.wordpress.com/
Дата: 29.03.11 01:55
Оценка: :)
Здравствуйте, divergo, Вы писали:

Главная проблема Linq в том, что он представляет собой всего одно выражение. Да, хранимки в общем случае могут быть быстрее. Но не потому что кешируется план запросов или какая-то фигня, а потому что в хранимке я могу такой код
SELECT
  X.*
FROM
  X
INNER JOIN
  Y ON Y.ID = X.ID
WHERE
  Y.Field = @Value

переписать вот так
DECLARE @PreFilteredY TABLE
(
  ID INT
);

INSERT INTO
  @PreFilteredY
SELECT
  ID
FROM
  Y
WHERE
  Y.Field = @Value

SELECT
  X.*
FROM
  X
INNER JOIN
  @PreFilteredY AS Y ON Y.ID = X.ID

и это (добро пожаловать в реальный мир) может в некоторых случаях работать существенно (на порядки) быстрее.

Кроме того, да, бизнес логику в SQL часто ругают, но иногда она нужна. Практически вся сложная аналитика либо пишется в SQL коде, либо в сервер приложений выгружается пол-базы почём зря. Когда эта база 5-6Гб, а запустили отчёт в полдень четверга, идеология отходит на второй план.
A journey of a thousand miles must begin with a single step © Lau Tsu
Re[2]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 29.03.11 02:53
Оценка: 1 (1)
Здравствуйте, adontz, Вы писали:

A>Главная проблема Linq в том, что он представляет собой всего одно выражение. Да, хранимки в общем случае могут быть быстрее. Но не потому что кешируется план запросов или какая-то фигня, а потому что в хранимке я могу такой код

A>переписать вот так

A>DECLARE @PreFilteredY TABLE
A>(
A>  ID INT
A>);

A>INSERT INTO
A>  @PreFilteredY
A>SELECT
A>  ID
A>FROM
A>  Y
A>WHERE
A>  Y.Field = @Value

A>SELECT
A>  X.*
A>FROM
A>  X
A>INNER JOIN
A>  @PreFilteredY AS Y ON Y.ID = X.ID

Под катом небольшой хелпер для DbManager:
  Скрытый текст
class MyDbManager : DbManager
{
    public Table<T> CreateTable<T>()
        where T : class
    {
        return CreateTable<T>(null);
    }

    public Table<T> CreateTable<T>(string tableName)
        where T : class
    {
        var table = new SqlTable<T>();
        var sb    = new StringBuilder();

        sb.AppendFormat("CREATE TABLE {0}\n(", tableName ?? table.Name);

        foreach (var field in table.Fields)
        {
            var f      = field.Value;
            var type   = SqlDataType.GetDataType(f.SystemType);
            var dbType = type.SqlDbType;
            var len    = type.Length > 0 ? "({0})".Args(type.Length) : type.Precision > 0 ? "({0},{1})".Args(type.Precision, type.Scale) : "";

            switch (dbType)
            {
                case SqlDbType.UniqueIdentifier :
                    dbType = SqlDbType.VarChar;
                    len    = "(36)";
                    break;
            }

            sb.AppendFormat("\n\t{0}\t{1}{2}\t{3}NULL{4},",
                f.PhysicalName,
                dbType,
                len,
                f.Nullable ? "" : "NOT ",
                f.IsIdentity ? "\t IDENTITY" : "");
        }

        sb.Length -= 1;
        sb.Append("\n)");

        SetCommand(sb.ToString());
        ExecuteNonQuery();

        var t = GetTable<T>();

        if (tableName != null)
            t = t.TableName(tableName);

        return t;
    }

    public void TruncateTable<T>()
        where T : class
    {
        var table = new SqlTable<T>();
        var sb    = new StringBuilder();

        sb.Append("TRUNCATE TABLE ");

        DataProvider.CreateSqlProvider().BuildTableName(sb, table.Database, table.Owner, table.Name);

        SetCommand(sb.ToString()).ExecuteNonQuery();
    }

    public void TruncateTable<T>(string dbName, string table)
        where T : class
    {
        var sb = new StringBuilder();

        sb.Append("TRUNCATE TABLE ");

        DataProvider.CreateSqlProvider().BuildTableName(sb, dbName, null, table);

        SetCommand(sb.ToString()).ExecuteNonQuery();
    }
}

[TableName("@PreFilteredY")
class PreFilteredY
{
    public int ID;
}

using (var db = new MyDbManager()
{
    var preFiltered = db.CreateTable<PreFilteredY>();

    db.GetTable<Y>
        .Where(y => y.Field = @Value)
        .Insert(preFiltered, y => new PreFilteredY { ID = y.ID });

    var q =
        from x in db.GetTable<X>()
        join p in preFiltered on x.ID equals p.ID
        select x;

    ...
}

A>и это (добро пожаловать в реальный мир) может в некоторых случаях работать существенно (на порядки) быстрее.

Добро пожаловать в мир BLToolkit

A>Кроме того, да, бизнес логику в SQL часто ругают, но иногда она нужна. Практически вся сложная аналитика либо пишется в SQL коде, либо в сервер приложений выгружается пол-базы почём зря. Когда эта база 5-6Гб, а запустили отчёт в полдень четверга, идеология отходит на второй план.


У нас и данных стотыщпицот гигабайт и логики не меньше. Тем не менее, с приходом Linq вся логика из базы была вычищена под корень. Ты даже не представляешь какое это счастье

Повторюсь ещё раз. Всё это не недостаток Linq в целом. Это недостатки конкретных реализаций Linq-провайдеров.
Если нам не помогут, то мы тоже никого не пощадим.
Re[3]: SQL(sp + view || Linq)
От: adontz Грузия http://adontz.wordpress.com/
Дата: 29.03.11 09:57
Оценка:
Здравствуйте, IT, Вы писали:

IT>Добро пожаловать в мир BLToolkit


Я не думаю, что ты действительно нуждаешься в моём объяснении разницы между table, temporary table и table variable.

A>>Кроме того, да, бизнес логику в SQL часто ругают, но иногда она нужна. Практически вся сложная аналитика либо пишется в SQL коде, либо в сервер приложений выгружается пол-базы почём зря. Когда эта база 5-6Гб, а запустили отчёт в полдень четверга, идеология отходит на второй план.

IT>У нас и данных стотыщпицот гигабайт и логики не меньше. Тем не менее, с приходом Linq вся логика из базы была вычищена под корень. Ты даже не представляешь какое это счастье

Представляю. Это недостижимое счастье.

IT>Повторюсь ещё раз. Всё это не недостаток Linq в целом. Это недостатки конкретных реализаций Linq-провайдеров.


Эквивалетное решение на Linq (пусть и с твоими расширениями, я не против) ты не предоставил.
A journey of a thousand miles must begin with a single step © Lau Tsu
Re[4]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 29.03.11 13:20
Оценка:
Здравствуйте, adontz, Вы писали:

IT>>Добро пожаловать в мир BLToolkit

A>Я не думаю, что ты действительно нуждаешься в моём объяснении разницы между table, temporary table и table variable.

Надеюсь тебе не надо объяснять как в приведённмо выше коде заменить слово CREATE на DECLARE?

IT>>Повторюсь ещё раз. Всё это не недостаток Linq в целом. Это недостатки конкретных реализаций Linq-провайдеров.

A>Эквивалетное решение на Linq (пусть и с твоими расширениями, я не против) ты не предоставил.

Это тебе будет домашнее задание "Ну, мы накидали идей, а вы теперь разгребайте!" (c) КВН.
Если нам не помогут, то мы тоже никого не пощадим.
Re[5]: SQL(sp + view || Linq)
От: adontz Грузия http://adontz.wordpress.com/
Дата: 29.03.11 13:30
Оценка:
Здравствуйте, IT, Вы писали:

IT>>>Добро пожаловать в мир BLToolkit

A>>Я не думаю, что ты действительно нуждаешься в моём объяснении разницы между table, temporary table и table variable.
IT>Надеюсь тебе не надо объяснять как в приведённмо выше коде заменить слово CREATE на DECLARE?

Осталось только убедиться, что это будет работать
A journey of a thousand miles must begin with a single step © Lau Tsu
Re[6]: SQL(sp + view || Linq)
От: Alexander Polyakov  
Дата: 30.03.11 11:53
Оценка:
Здравствуйте, IT, Вы писали:

IT>... не позволяет вводить абстракции ...

а какие абстракции позволяет вводить LINQ?
Re[7]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 30.03.11 13:25
Оценка:
Здравствуйте, Alexander Polyakov, Вы писали:

IT>>... не позволяет вводить абстракции ...

AP>а какие абстракции позволяет вводить LINQ?

C# умеет. Ну и Linq как следствие. Например, можно абстрагироваться от деталей конкретной СУБД.
Если нам не помогут, то мы тоже никого не пощадим.
Re[8]: SQL(sp + view || Linq)
От: Alexander Polyakov  
Дата: 30.03.11 14:22
Оценка: +1 :)
Здравствуйте, IT, Вы писали:

IT>C# умеет. Ну и Linq как следствие.

LINQ это лишь подмножество C#-а, поэтому то что умеет C# не обязательно умеет LINQ. Поэтому никакого прямого следствия нет, и требуется доказательство -- примеры абстракций; их я у тебя и запросил.

IT>Например, можно абстрагироваться от деталей конкретной СУБД.

Ааа, это. Такие абстракции нам и даром не нужны . Нам существенно лучше без них.
Вообще, если каждую обертку называть словом “абстракция”, то это просто издевательство над понятием “абстракция”.
Re[9]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 30.03.11 14:49
Оценка:
Здравствуйте, Alexander Polyakov, Вы писали:

IT>>C# умеет. Ну и Linq как следствие.

AP>LINQ это лишь подмножество C#-а, поэтому то что умеет C# не обязательно умеет LINQ. Поэтому никакого прямого следствия нет, и требуется доказательство -- примеры абстракций; их я у тебя и запросил.

Сам додумался или где-то прочитал?
Вообще-то Linq это уже сама по себе абстракция. Позволяет в определённом смысле абстрагироваться от типа источника данных.

IT>>Например, можно абстрагироваться от деталей конкретной СУБД.

AP>Ааа, это. Такие абстракции нам и даром не нужны . Нам существенно лучше без них.
AP>Вообще, если каждую обертку называть словом “абстракция”, то это просто издевательство над понятием “абстракция”.

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

Если же ты беспокоишься об эффективности сгенерированного SQL, то опять же это не проблема Linq в целом, это проблема конкретных реализаций.
Если нам не помогут, то мы тоже никого не пощадим.
Re: SQL(sp + view || Linq)
От: Cyberax Марс  
Дата: 30.03.11 14:52
Оценка:
Здравствуйте, divergo, Вы писали:

D>Навеяно опросом
Автор: Shmj
Дата: 06.03.11
Вопрос: Язык SQL не очень удобен для написания логики. Но иногда полезно писать основную логику приложения в триггерах и хранимых процедурах для сокращения передаваемых данных (между базой и приложением). Как вы решаете данную проблему?
и рабочей ситуацией.

D>Есть задача перевода на Linq приложения построенного на основе датасетов, хранимых процедур и представлений.
Хранимые процедуры должны умереть (в 99% случаев) — это вообще не вопрос.

А вот чем и как их заменять — можно пообсуждать.
Sapienti sat!
Re[10]: SQL(sp + view || Linq)
От: Alexander Polyakov  
Дата: 30.03.11 15:04
Оценка:
Здравствуйте, IT, Вы писали:

IT>Здравствуйте, Alexander Polyakov, Вы писали:


IT>>>C# умеет. Ну и Linq как следствие.

AP>>LINQ это лишь подмножество C#-а, поэтому то что умеет C# не обязательно умеет LINQ. Поэтому никакого прямого следствия нет, и требуется доказательство -- примеры абстракций; их я у тебя и запросил.

IT>Сам додумался или где-то прочитал?

IT>Вообще-то Linq это уже сама по себе абстракция. Позволяет в определённом смысле абстрагироваться от типа источника данных.

IT>>>Например, можно абстрагироваться от деталей конкретной СУБД.

AP>>Ааа, это. Такие абстракции нам и даром не нужны . Нам существенно лучше без них.
AP>>Вообще, если каждую обертку называть словом “абстракция”, то это просто издевательство над понятием “абстракция”.

IT>Совершенно напрасно. Linq позволет экономить кучу времени не только благодаря типизации, но и более компактной и понятной записи запроса, убирая из него ненужные детали.


IT>Если же ты беспокоишься об эффективности сгенерированного SQL, то опять же это не проблема Linq в целом, это проблема конкретных реализаций.


Больше примеров полезных абстракций мы так и не дождемся?

В твоем последнем посте пошла чистая вода из евангелистических опусов (я это уже всё читал).
Re[3]: SQL(sp + view || Linq)
От: _FRED_ Черногория
Дата: 30.03.11 15:20
Оценка:
Здравствуйте, IT, Вы писали:

IT>Под катом небольшой хелпер для DbManager:


А что, провайдеры (или что там отвечает за абстракцию от кнкретной БД) не умеют по информации о типе возвращать строку с описанием типа?
Или нет готового метода, который по филду создаст строку с декларацией этого филда?
Это пока ещё небыло нужно в тулките или каждый раз приходится вручную делать?
Help will always be given at Hogwarts to those who ask for it.
Re[11]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 30.03.11 15:33
Оценка:
Здравствуйте, Alexander Polyakov, Вы писали:

AP>Больше примеров полезных абстракций мы так и не дождемся?


Да без проблем. Нужно только прояснить один вопрос — что в твоём понимании означает "полезных"? Иначе этот разговор ни о чём, все примеры будут относится к категории бесполезных и непонятно зачем тогда вообще тратить время.

AP>В твоем последнем посте пошла чистая вода из евангелистических опусов (я это уже всё читал).


Задача евангелистов — ликвидация безграмотности. Раз уж меня записали в евангелисты, то, если хочешь, могу продемонстрировать несколько примеров, в которых запросы на Linq просты и понятны, а получающийся SQL уже не так очевиден.
Если нам не помогут, то мы тоже никого не пощадим.
Re[5]: SQL(sp + view || Linq)
От: adontz Грузия http://adontz.wordpress.com/
Дата: 30.03.11 15:34
Оценка:
Здравствуйте, IT, Вы писали:

Из профессионального любопытства: как будет выглядеть выборка из параметризуемой функции?
A journey of a thousand miles must begin with a single step © Lau Tsu
Re[4]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 30.03.11 15:40
Оценка:
Здравствуйте, _FRED_, Вы писали:

_FR>Это пока ещё небыло нужно в тулките или каждый раз приходится вручную делать?


Не нужно было. Вручную делать приходилось ровно один раз.
Если нам не помогут, то мы тоже никого не пощадим.
Re[6]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 30.03.11 15:40
Оценка:
Здравствуйте, adontz, Вы писали:

A>Из профессионального любопытства: как будет выглядеть выборка из параметризуемой функции?


Лучше сразу напиши SQL, а я тебе тогда Linq.
Если нам не помогут, то мы тоже никого не пощадим.
Re[7]: SQL(sp + view || Linq)
От: adontz Грузия http://adontz.wordpress.com/
Дата: 30.03.11 15:49
Оценка:
Здравствуйте, IT, Вы писали:

IT>Лучше сразу напиши SQL, а я тебе тогда Linq.


Есть функция GetCustomers, которая возвращает записи о клиентах на конкретный момент времени (активен/пассивен, тариф, активная ли скидка, другие зависящие от момента времени параметры)
CREATE FUNCTION [GetCustomers](
    @Timestamp DATETIME2)
RETURN TABLE
WITH SCHEMABINDING
AS
RETURN
(
    ...
)

Запрос не очень тяжёлый (большинство таблиц не большие), но содержащий кучу джойнов. Практика показала, что от выделения его в функцию производительность если и пострадала, то незаметно. А вот жить стало легче. Функция используется в куче разных мест. Возьмём простейший фильтрующий запрос
SELECT
    *
FROM
    [GetCustomers](@Timestamp)
WHERE
    [LastName] LIKE '%кач%'


Интересует как аналогичная сиутация выглядит в Linq любой модификации.
A journey of a thousand miles must begin with a single step © Lau Tsu
Re[8]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 30.03.11 16:00
Оценка:
Здравствуйте, adontz, Вы писали:

A>SELECT
A>    *
A>FROM
A>    [GetCustomers](@Timestamp)
A>WHERE
A>    [LastName] LIKE '%кач%'


A>Интересует как аналогичная сиутация выглядит в Linq любой модификации.


Linq 2 SQL умеет генерировать обёртки для таких функций. Для BLToolkit пока нужно описывать их руками. Результирующий код будет таким:

var q =
    from c in GetCustomers(timestamp)
    where c.LastName.Contains("кач")
    select c;
Если нам не помогут, то мы тоже никого не пощадим.
Re[3]: SQL(sp + view || Linq)
От: Sshur Россия http://shurygin-sergey.livejournal.com
Дата: 30.03.11 18:46
Оценка:
Здравствуйте, IT, Вы писали:

IT>Повторюсь ещё раз. Всё это не недостаток Linq в целом. Это недостатки конкретных реализаций Linq-провайдеров.



у Linq2SQL помнится проблема была с left join, их там просто нет, либо есть но с ограничениями. И какие еще есть реализации линк-провайдеров?
Шурыгин Сергей

"Не следует преумножать сущности сверх необходимости" (с) Оккам
Re[12]: SQL(sp + view || Linq)
От: Alexander Polyakov  
Дата: 30.03.11 18:52
Оценка:
Здравствуйте, IT, Вы писали:

IT>... могу продемонстрировать несколько примеров, в которых запросы на Linq просты и понятны, а получающийся SQL уже не так очевиден.

Это уже похоже на что-то интересное, только фразу “а получающийся SQL уже не так очевиден” надо заменить на “а на SQL человек не сможет записать этот запрос в понятной и очевидной форме”. Если в такой формулировке, тогда, да, продемонстрируй, будет интересно. Человеком, записывающим запрос на SQL, буду я.
Re[4]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 30.03.11 19:00
Оценка:
Здравствуйте, Sshur, Вы писали:

S>у Linq2SQL помнится проблема была с left join, их там просто нет, либо есть но с ограничениями. И какие еще есть реализации линк-провайдеров?


Всё там есть. Другое дело, что это тот самый случай, когда выразительность Linq не на высоте. Вот LEFT JOIN:

from p in db.Product
join c in db.Category on p.CategoryID equals c.CategoryID into g
from c in g.DefaultIfEmpty()
select new
{
    c.CategoryName,
    p.ProductName
};

Некоторые Linq-провайдеры вводят свои методы LeftJoin, кажется DataObjects это точно умеет. Можно их заменять ассоциациями. Например, приведённый выше пример при соответствующем объявлении ассоциации эквивалентен следующему:

from p in db.Product
select new
{
    p.Category.CategoryName,
    p.ProductName
};

BLToolkit по объявлению ассоциации определяет какой Join использовать. Насчёт Linq 2 SQL не уверен.
Если нам не помогут, то мы тоже никого не пощадим.
Re[5]: SQL(sp + view || Linq)
От: Sshur Россия http://shurygin-sergey.livejournal.com
Дата: 30.03.11 19:20
Оценка:
Здравствуйте, IT, Вы писали:

IT>Здравствуйте, Sshur, Вы писали:


S>>у Linq2SQL помнится проблема была с left join, их там просто нет, либо есть но с ограничениями. И какие еще есть реализации линк-провайдеров?


IT>Всё там есть. Другое дело, что это тот самый случай, когда выразительность Linq не на высоте. Вот LEFT JOIN:


Update ... from ...?

Есть ли возможность написать пусть даже простой update без перетаскивания всех строк на клиента? У меня в проекте с линк2sql на каждый update стоит db.ExecuteCommand("UPDATE...");
Шурыгин Сергей

"Не следует преумножать сущности сверх необходимости" (с) Оккам
Re[5]: SQL(sp + view || Linq)
От: Alexander Polyakov  
Дата: 30.03.11 21:46
Оценка:
Здравствуйте, IT, Вы писали:

IT>Некоторые Linq-провайдеры вводят свои методы LeftJoin, кажется DataObjects это точно умеет.

Ха-ха, дополнительными методами проблема LEFT JOIN-ов нормально не решается. На самом деле, если начать копать проблему LEFT JOIN-ов, то оказывается, что она залегает ух как глубоко, и ее хорошее решение куча всего затронет (скорее всего, сам язык C#). А создатели LINQ всё это тупо замели под ковер, заставляя пользователей мучаться с этим “мелким” недостатком.

Если интересно могу расписать подробнее что там с LEFT JOIN-ами, но это не выйдет кратко.
Re[6]: SQL(sp + view || Linq)
От: adontz Грузия http://adontz.wordpress.com/
Дата: 30.03.11 22:08
Оценка: +1
Здравствуйте, Alexander Polyakov, Вы писали:

AP>Если интересно могу расписать подробнее что там с LEFT JOIN-ами, но это не выйдет кратко.


Мне интересно.
A journey of a thousand miles must begin with a single step © Lau Tsu
Re[6]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 31.03.11 03:59
Оценка:
Здравствуйте, Sshur, Вы писали:

S>Update ... from ...?

S>Есть ли возможность написать пусть даже простой update без перетаскивания всех строк на клиента? У меня в проекте с линк2sql на каждый update стоит db.ExecuteCommand("UPDATE...");

http://bltoolkit.net/Doc.LinqExtensions.ashx#Update_2

Это не Linq 2 SQL, но это Linq.
Если нам не помогут, то мы тоже никого не пощадим.
Re[6]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 31.03.11 04:01
Оценка: +1
Здравствуйте, Alexander Polyakov, Вы писали:

AP>Если интересно могу расписать подробнее что там с LEFT JOIN-ами, но это не выйдет кратко.


Будет интересно.
Если нам не помогут, то мы тоже никого не пощадим.
Re[7]: SQL(sp + view || Linq)
От: Sshur Россия http://shurygin-sergey.livejournal.com
Дата: 31.03.11 06:17
Оценка:
Здравствуйте, IT, Вы писали:

IT>Здравствуйте, Sshur, Вы писали:


S>>Update ... from ...?

S>>Есть ли возможность написать пусть даже простой update без перетаскивания всех строк на клиента? У меня в проекте с линк2sql на каждый update стоит db.ExecuteCommand("UPDATE...");

IT>http://bltoolkit.net/Doc.LinqExtensions.ashx#Update_2


IT>Это не Linq 2 SQL, но это Linq.


Доп метод .Update не часть языка. Соответсвенно это не Language INtegrated Query, коими являются запросы типа from e in employes select e.Id. Разве не так?


Методов расширения, которые будут типизированные параметры принимать, можно хоть для DataSet наделать
Шурыгин Сергей

"Не следует преумножать сущности сверх необходимости" (с) Оккам
Re[8]: SQL(sp + view || Linq)
От: _FRED_ Черногория
Дата: 31.03.11 10:13
Оценка:
Здравствуйте, Sshur, Вы писали:

S>>>Update ... from ...?

S>>>Есть ли возможность написать пусть даже простой update без перетаскивания всех строк на клиента? У меня в проекте с линк2sql на каждый update стоит db.ExecuteCommand("UPDATE...");
IT>>http://bltoolkit.net/Doc.LinqExtensions.ashx#Update_2
IT>>Это не Linq 2 SQL, но это Linq.

S>Доп метод .Update не часть языка. Соответсвенно это не Language INtegrated Query, коими являются запросы типа from e in employes select e.Id. Разве не так?

S>Методов расширения, которые будут типизированные параметры принимать, можно хоть для DataSet наделать

Была бы библиотека c реализацией, а уж найти Language в который подобный Query можно сделать как INtegrated — задача более чем решаемая
Help will always be given at Hogwarts to those who ask for it.
Re[9]: SQL(sp + view || Linq)
От: adontz Грузия http://adontz.wordpress.com/
Дата: 31.03.11 10:39
Оценка:
Здравствуйте, _FRED_, Вы писали:

_FR>Была бы библиотека c реализацией, а уж найти Language в который подобный Query можно сделать как INtegrated — задача более чем решаемая


Nemerle?
A journey of a thousand miles must begin with a single step © Lau Tsu
Re[10]: SQL(sp + view || Linq)
От: _FRED_ Черногория
Дата: 31.03.11 10:44
Оценка:
Здравствуйте, adontz, Вы писали:

_FR>>Была бы библиотека c реализацией, а уж найти Language в который подобный Query можно сделать как INtegrated — задача более чем решаемая


A>Nemerle?


"Заметьте, не я это предложил"
Help will always be given at Hogwarts to those who ask for it.
Re[8]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 31.03.11 13:13
Оценка:
Здравствуйте, Sshur, Вы писали:

S>Доп метод .Update не часть языка. Соответсвенно это не Language INtegrated Query, коими являются запросы типа from e in employes select e.Id. Разве не так?


Не так. Query Comprehension Syntax покрывает едва ли половину всех функций Linq. Из того, что не покрывается: все агрегатные функции (Count, Min, Max, Average), Contains, Any, All, Intersect, Except, Union, Concat, Take, Skip, DefaultIfEmpty, First(OrDefault), Single(OrDefault), ElementAt, наверняка ещё что-то забыл.

S>Методов расширения, которые будут типизированные параметры принимать, можно хоть для DataSet наделать


Для DataSet можно написать чего угодно. Для Linq 2 SQL нельзя написать ничего. Насколько мне известно, расширяемых провайдеров в природе пока не существует, хотя скоро появятся. Но даже если бы они и были, то написание своего расширения задача очень и очень нетривиальная.
Если нам не помогут, то мы тоже никого не пощадим.
Re[9]: SQL(sp + view || Linq)
От: Sshur Россия http://shurygin-sergey.livejournal.com
Дата: 31.03.11 15:04
Оценка: :)
Здравствуйте, _FRED_, Вы писали:


S>>Доп метод .Update не часть языка. Соответсвенно это не Language INtegrated Query, коими являются запросы типа from e in employes select e.Id. Разве не так?

S>>Методов расширения, которые будут типизированные параметры принимать, можно хоть для DataSet наделать

_FR>Была бы библиотека c реализацией, а уж найти Language в который подобный Query можно сделать как INtegrated — задача более чем решаемая



Угу, напишем свой SQL, с блекджеком и шлю типизацией
Шурыгин Сергей

"Не следует преумножать сущности сверх необходимости" (с) Оккам
Re[7]: SQL(sp + view || Linq)
От: Alexander Polyakov  
Дата: 31.03.11 18:13
Оценка: 54 (1)
Здравствуйте, IT, Вы писали:

AP>>Если интересно могу расписать подробнее что там с LEFT JOIN-ами, но это не выйдет кратко.

IT>Будет интересно.
1. Если требуется join-нить несколько таблиц (больше двух), то без query comprehension хреново, потому что вложенные лямбды дают экспоненциальную сложность при компиляции, а писать такие запросы вручную без вложенных лямбд это кошмар. Поэтому единственное спасение query comprehension. Но в C# query comprehension это не просто дополнительный метод, а уже часть языка. Т.е. надо вводить оператор left join на уровне языка.

2. Если взять SQL запросы:
SELECT Bbb.AaaId FROM Aaa INNER JOIN Bbb ON Aaa.A001 = Bbb.B001
SELECT Bbb.AaaId FROM Aaa LEFT JOIN Bbb ON Aaa.A001 = Bbb.B001

И запросить column metadata, например, с помощью метода SqlDataReader.GetSchemaTable, то мы получим, что для столбца Bbb.AaaId в первом случае AllowDBNull=false, а во втором AllowDBNull=true.
Как такое поддержать (естественно, на этапе компиляции) с помощью введения только метода?

3. Если рассмотреть предыдущие пункты в совокупности:
from aaa in Aaa
join bbb in Bbb
    on aaa.A001 equals bbb.B001 /*здесь aaa.A001 еще not nullable*/
right join ccc in Ccc
    on aaa.A001 equals ccc.C001 /*здесь aaa.A001 еще not nullable*/
join ddd in Ddd
    on aaa.A001 equals ddd.D001 /*здесь aaa.A001 уже nullable*/
select
    aaa.A002 /*nullable из-за второго right join-а*/
    ссс.С002 /*not nullable*/
Как это всё поддерживать на этапе компиляции? Без изменения языка не обойтись.
Re[8]: SQL(sp + view || Linq)
От: gandjustas Россия http://blog.gandjustas.ru/
Дата: 31.03.11 18:59
Оценка:
Здравствуйте, Alexander Polyakov, Вы писали:

AP>Здравствуйте, IT, Вы писали:


AP>>>Если интересно могу расписать подробнее что там с LEFT JOIN-ами, но это не выйдет кратко.

IT>>Будет интересно.
AP>1. Если требуется join-нить несколько таблиц (больше двух), то без query comprehension хреново, потому что вложенные лямбды дают экспоненциальную сложность при компиляции, а писать такие запросы вручную без вложенных лямбд это кошмар. Поэтому единственное спасение query comprehension.
Не понял, от чего спасение? query comprehension рассахариваются в такие же вызовы, как писать руками.

AP>Но в C# query comprehension это не просто дополнительный метод, а уже часть языка. Т.е. надо вводить оператор left join на уровне языка.

Непонятно зачем оно нужно.

AP>2. Если взять SQL запросы:

AP>
AP>SELECT Bbb.AaaId FROM Aaa INNER JOIN Bbb ON Aaa.A001 = Bbb.B001
AP>SELECT Bbb.AaaId FROM Aaa LEFT JOIN Bbb ON Aaa.A001 = Bbb.B001
AP>

AP>И запросить column metadata, например, с помощью метода SqlDataReader.GetSchemaTable, то мы получим, что для столбца Bbb.AaaId в первом случае AllowDBNull=false, а во втором AllowDBNull=true.
AP>Как такое поддержать (естественно, на этапе компиляции) с помощью введения только метода?
Зачем подержать? Можешь сказать как поменяется семантика значений в данном случае?
Что-то есть подозрение что семантика будет закладываться в модель, а не в запрос.

AP>3. Если рассмотреть предыдущие пункты в совокупности:

AP>
AP>from aaa in Aaa
AP>join bbb in Bbb
AP>    on aaa.A001 equals bbb.B001 /*здесь aaa.A001 еще not nullable*/
AP>right join ccc in Ccc
AP>    on aaa.A001 equals ccc.C001 /*здесь aaa.A001 еще not nullable*/
AP>join ddd in Ddd
AP>    on aaa.A001 equals ddd.D001 /*здесь aaa.A001 уже nullable*/
AP>select
AP>    aaa.A002 /*nullable из-за второго right join-а*/
AP>    ссс.С002 /*not nullable*/
AP>

Как это всё поддерживать на этапе компиляции? Без изменения языка не обойтись.
А какой смысл писать руками джоины? Это все можно внести в модель и пользоваться навигационными свойствами, запрос станет однозначнее и короче.

Вот только ты не любишь семантику приводить.
Re[8]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 31.03.11 19:00
Оценка:
Здравствуйте, Alexander Polyakov, Вы писали:

AP>[/c#] Как это всё поддерживать на этапе компиляции? Без изменения языка не обойтись.


На самом деле это более общая проблема чем LEFT JOIN. Как быть, например, в следующей ситуации?

from t in
    db.Table.Select(t => new Table { Field1 = t.Field1 }).Union(
    db.Table.Select(t => new Table { Field2 = t.Field2 }));
where ...
Если нам не помогут, то мы тоже никого не пощадим.
Re[9]: SQL(sp + view || Linq)
От: Alexander Polyakov  
Дата: 31.03.11 22:52
Оценка:
Здравствуйте, IT, Вы писали:

IT>На самом деле это более общая проблема чем LEFT JOIN. Как быть, например, в следующей ситуации?

В твоем примере нет никакой проблемы. Nullability колонок четко содержится в определении класса (типа) Table. А вот в случае LEFT JOIN-на nullability колонок уже не определяется только классами “таблиц”, участвующих в join-е; на nullability колонок оказывает влияние еще сама операция left/right join. Более того, как показано в моем посте выше, одно и тоже выражение aaa.A001 может иметь разную nullability в разных участках одного запроса.
Re[10]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 31.03.11 23:20
Оценка:
Здравствуйте, Alexander Polyakov, Вы писали:

IT>>На самом деле это более общая проблема чем LEFT JOIN. Как быть, например, в следующей ситуации?

AP>В твоем примере нет никакой проблемы. Nullability колонок четко содержится в определении класса (типа) Table.

Вот определение класса:

class Table
{
    public int Field1;
    public int Field2;
}

Никаких null.

А вот соответсвующий SQL:

SELECT Field1, NULL FROM Table1
UNION
SELECT NULL, Field2 FROM Table1

К классе не nullable, а в жизни nullable.

AP>А вот в случае LEFT JOIN-на nullability колонок уже не определяется только классами “таблиц”, участвующих в join-е; на nullability колонок оказывает влияние еще сама операция left/right join. Более того, как показано в моем посте выше, одно и тоже выражение aaa.A001 может иметь разную nullability в разных участках одного запроса.


И здесь оно разное. Добавь WHERE в любой селект и получишь что тебе надо.

На самом деле всё это ерунда. Проблема есть конечно, но не такая большая.
Если нам не помогут, то мы тоже никого не пощадим.
Re[11]: SQL(sp + view || Linq)
От: Alexander Polyakov  
Дата: 01.04.11 00:28
Оценка:
Здравствуйте, IT, Вы писали:

IT>Вот определение класса:


IT>
IT>class Table
IT>{
IT>    public int Field1;
IT>    public int Field2;
IT>}
IT>

IT>Никаких null.
IT>А вот соответсвующий SQL:
IT>
IT>SELECT Field1, NULL FROM Table1
IT>UNION
IT>SELECT NULL, Field2 FROM Table1
IT>

IT>К классе не nullable, а в жизни nullable.
Ты, кажется, не понимаешь про LEFT JOIN.

Попробую объяснить с другой стороны. Если отказаться от LINQ и использовать, скажем, stored procedures или просто запросы и какую-либо тулзу для генерирования классов для result set-ов (которая внутри использует метод типа SqlDataReader.GetSchemaTable), тогда для вот такого запроса:
SELECT Bbb.AaaId FROM Aaa LEFT JOIN Bbb ON Aaa.A001 = Bbb.B001
сгенерируется класс
class QueryResult1
{
public int? AaaId;
}
А для такого запроса:
SELECT Bbb.AaaId FROM Aaa INNER JOIN Bbb ON Aaa.A001 = Bbb.B001
class QueryResult2
{
public int AaaId;
}

Зачем ты выписал SQL запрос, если у тебя LINQ, я не понял. Но если плясать от твоего SQL запроса, то метод SqlDataReader.GetSchemaTable для такого запроса сгенерирует класс:
class Table
{
public int? Field1;
public int? Field2;
}
Вместо генерации, естественно, можно использовать просто верификацию, т.е. и запрос и класс пишутся руками, а тулза лишь проверяет их на совместимость. В твоем примере тулза выдаст ошибку о том, что запрос
SELECT Field1, NULL FROM Table1
UNION
SELECT NULL, Field2 FROM Table1
не совместим с классом:
class Table
{
public int Field1;
public int Field2;
}

Вот что-то подобное и хотелось бы иметь в C#-е -- такую поддержку проверок nullability для LEFT JOIN-ов на этапе компиляции.
Re[12]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 01.04.11 03:39
Оценка:
Здравствуйте, Alexander Polyakov, Вы писали:

IT>>К классе не nullable, а в жизни nullable.

AP>Ты, кажется, не понимаешь про LEFT JOIN.

Я, кажется, не понимаю серьёзности поднятой тобой проблемы. Зачем мне генерировать классы под каждый запрос?
Если нам не помогут, то мы тоже никого не пощадим.
Re[13]: SQL(sp + view || Linq)
От: adontz Грузия http://adontz.wordpress.com/
Дата: 01.04.11 03:40
Оценка:
Здравствуйте, IT, Вы писали:

IT>Я, кажется, не понимаю серьёзности поднятой тобой проблемы. Зачем мне генерировать классы под каждый запрос?


А разве анонимные типы не генерируются компилятором?
A journey of a thousand miles must begin with a single step © Lau Tsu
Re[14]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 01.04.11 05:04
Оценка:
Здравствуйте, adontz, Вы писали:

IT>>Я, кажется, не понимаю серьёзности поднятой тобой проблемы. Зачем мне генерировать классы под каждый запрос?

A>А разве анонимные типы не генерируются компилятором?

А разве ты не сам определяешь то, что генерирует компилятор?
Если нам не помогут, то мы тоже никого не пощадим.
Re[15]: SQL(sp + view || Linq)
От: adontz Грузия http://adontz.wordpress.com/
Дата: 01.04.11 05:05
Оценка:
Здравствуйте, IT, Вы писали:

IT>>>Я, кажется, не понимаю серьёзности поднятой тобой проблемы. Зачем мне генерировать классы под каждый запрос?

A>>А разве анонимные типы не генерируются компилятором?
IT>А разве ты не сам определяешь то, что генерирует компилятор?

Я так понимаю проблема в том, что компилятор либо должен все поля генерировать Nullable (что, даже если плюнуть на производительность, просто неудобно в использовании), либо будут ошибки времени выполнения.
A journey of a thousand miles must begin with a single step © Lau Tsu
Re[16]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 01.04.11 05:36
Оценка:
Здравствуйте, adontz, Вы писали:

A>Я так понимаю проблема в том, что компилятор либо должен все поля генерировать Nullable (что, даже если плюнуть на производительность, просто неудобно в использовании), либо будут ошибки времени выполнения.


Компилятор сгенерирует то, что ему скажут. С какой стати он начнёт генерировать без твоего разрешения Nullable? Про ошибки времени выполнения я честно говоря не понял.
Если нам не помогут, то мы тоже никого не пощадим.
Re[17]: SQL(sp + view || Linq)
От: adontz Грузия http://adontz.wordpress.com/
Дата: 01.04.11 09:53
Оценка:
Здравствуйте, IT, Вы писали:

A>>Я так понимаю проблема в том, что компилятор либо должен все поля генерировать Nullable (что, даже если плюнуть на производительность, просто неудобно в использовании), либо будут ошибки времени выполнения.

IT>Компилятор сгенерирует то, что ему скажут. С какой стати он начнёт генерировать без твоего разрешения Nullable? Про ошибки времени выполнения я честно говоря не понял.

Как сказать что нужен Nullable в случае outer join: left. right, cross, не суть?
Что будет если в поле не Nullable типа попытаться записать null?
A journey of a thousand miles must begin with a single step © Lau Tsu
Re[15]: SQL(sp + view || Linq)
От: Alexander Polyakov  
Дата: 01.04.11 11:08
Оценка:
Здравствуйте, IT, Вы писали:

IT>А разве ты не сам определяешь то, что генерирует компилятор?

Смотри, если переписать твой пример вот так:
db.Table.Select(t => new { Field1 = t.Field1, Field2 = new int?() }).Union(
db.Table.Select(t => new { Field1 = new int?(), Field2 = t.Field2 }))
.Select(t => new Table { Field1 = t.Field1, Field2 = t.Field2 })
то будет ошибка компиляции в третьей строчке (уже в текущей версии C#).

Аналогично для LEFT JOIN
from aaa in Aaa
left join bbb in Bbb
on aaa.A001 equals bbb.B001
select new { bbb.B001, bbb.B002 };
в анонимном класса поля B001 и B002 должны быть nullable даже, если изначальные поля Bbb.B001 и Bbb.B002 not nullable.
Re[16]: SQL(sp + view || Linq)
От: gandjustas Россия http://blog.gandjustas.ru/
Дата: 01.04.11 12:05
Оценка:
Здравствуйте, Alexander Polyakov, Вы писали:

AP>Здравствуйте, IT, Вы писали:


IT>>А разве ты не сам определяешь то, что генерирует компилятор?

AP>Смотри, если переписать твой пример вот так:
AP>db.Table.Select(t => new { Field1 = t.Field1, Field2 = new int?() }).Union(
AP>db.Table.Select(t => new { Field1 = new int?(), Field2 = t.Field2 }))
AP>.Select(t => new Table { Field1 = t.Field1, Field2 = t.Field2 })
AP>то будет ошибка компиляции в третьей строчке (уже в текущей версии C#).

AP>Аналогично для LEFT JOIN

AP>from aaa in Aaa
AP>left join bbb in Bbb
AP>on aaa.A001 equals bbb.B001
AP>select new { bbb.B001, bbb.B002 };
AP>в анонимном класса поля B001 и B002 должны быть nullable даже, если изначальные поля Bbb.B001 и Bbb.B002 not nullable.

Коме должны?

Если логика обрабатывающая результаты запроса опирается на не_null значение колонки, то упадет в любом случае. Если колонка может быть nullable, то это лучше всего описать явно в самом linq запросе, без неявной генерации nullable значений.
Re[17]: SQL(sp + view || Linq)
От: adontz Грузия http://adontz.wordpress.com/
Дата: 01.04.11 12:06
Оценка:
Здравствуйте, gandjustas, Вы писали:

G>Если колонка может быть nullable, то это лучше всего описать явно в самом linq запросе, без неявной генерации nullable значений.


Это называется "костыли".
A journey of a thousand miles must begin with a single step © Lau Tsu
Re[18]: SQL(sp + view || Linq)
От: gandjustas Россия http://blog.gandjustas.ru/
Дата: 01.04.11 12:19
Оценка:
Здравствуйте, adontz, Вы писали:

A>Здравствуйте, gandjustas, Вы писали:


G>>Если колонка может быть nullable, то это лучше всего описать явно в самом linq запросе, без неявной генерации nullable значений.


A>Это называется "костыли".


А вариант править семантику Linq просто потому что в SQL такое поведение? В SQL вообще дофигища неявных преобразований, все в .NET тащить? А сколько диалектов этого SQL еще...
Все равно все упрется в семантику тех данных, которые достаются из базы. Если приходит nullable, а требуется не nullable, то придется ставить подпорки чтобы все заработало.
Re[18]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 01.04.11 13:24
Оценка:
Здравствуйте, adontz, Вы писали:

A>Как сказать что нужен Nullable в случае outer join: left. right, cross, не суть?


Пример такой ситуации можешь привести?

A>Что будет если в поле не Nullable типа попытаться записать null?


Как минимум запишется default(T).
Если нам не помогут, то мы тоже никого не пощадим.
Re[16]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 01.04.11 13:32
Оценка:
Здравствуйте, Alexander Polyakov, Вы писали:

IT>>А разве ты не сам определяешь то, что генерирует компилятор?

AP>Смотри, если переписать твой пример вот так:
AP>db.Table.Select(t => new { Field1 = t.Field1, Field2 = new int?() }).Union(
AP>db.Table.Select(t => new { Field1 = new int?(), Field2 = t.Field2 }))
AP>.Select(t => new Table { Field1 = t.Field1, Field2 = t.Field2 })
AP>то будет ошибка компиляции в третьей строчке (уже в текущей версии C#).

Ошибка будет раньше.

AP>Аналогично для LEFT JOIN

AP>from aaa in Aaa
AP>left join bbb in Bbb
AP>on aaa.A001 equals bbb.B001
AP>select new { bbb.B001, bbb.B002 };
AP>в анонимном класса поля B001 и B002 должны быть nullable даже, если изначальные поля Bbb.B001 и Bbb.B002 not nullable.

Это всё решается.

from aaa in Aaa
left join bbb in Bbb
on aaa.A001 equals bbb.B001
select new
{
    // если тебе нужен весь объект, то он будет null
    bbb,
    // если отдельное поле
    B001 = bbb == null ? (int?)null : bbb.B001,
    B002 = bbb == null ? (int?)null : bbb.B002
};

Как юы ты решал аналогичную проблему, если бы писал код для Linq 2 Objects? Вот так же делай и для Linq 2 SQL и всё получится.
Если нам не помогут, то мы тоже никого не пощадим.
Re[19]: SQL(sp + view || Linq)
От: adontz Грузия http://adontz.wordpress.com/
Дата: 01.04.11 13:44
Оценка:
Здравствуйте, gandjustas, Вы писали:

G>А вариант править семантику Linq просто потому что в SQL такое поведение? В SQL вообще дофигища неявных преобразований, все в .NET тащить? А сколько диалектов этого SQL еще...

G>Все равно все упрется в семантику тех данных, которые достаются из базы. Если приходит nullable, а требуется не nullable, то придется ставить подпорки чтобы все заработало.

outer join не имеет большого отношения именно к SQL. Это достаточно понятная процедура над множествами сама по себе.
A journey of a thousand miles must begin with a single step © Lau Tsu
Re[19]: SQL(sp + view || Linq)
От: adontz Грузия http://adontz.wordpress.com/
Дата: 01.04.11 13:46
Оценка:
Здравствуйте, IT, Вы писали:

A>>Как сказать что нужен Nullable в случае outer join: left. right, cross, не суть?

IT>Пример такой ситуации можешь привести?

Пример чего, right outer join? Вот есть right join, как сказать что связываемые поля должны (или не должны) быть nullable.

A>>Что будет если в поле не Nullable типа попытаться записать null?

IT>Как минимум запишется default(T).

Для value типов это весьма некорректно.
A journey of a thousand miles must begin with a single step © Lau Tsu
Re[20]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 01.04.11 14:12
Оценка:
Здравствуйте, adontz, Вы писали:

A>>>Как сказать что нужен Nullable в случае outer join: left. right, cross, не суть?

IT>>Пример такой ситуации можешь привести?

A>Пример чего, right outer join? Вот есть right join, как сказать что связываемые поля должны (или не должны) быть nullable.


Зачем так много говорить, напиши код и мы его разберём.

A>>>Что будет если в поле не Nullable типа попытаться записать null?

IT>>Как минимум запишется default(T).

A>Для value типов это весьма некорректно.


Да ладно.

class A
{
    public int Field1;
    public int Field2;
}

new A { Field1 = 1 };

Корректно?
Если нам не помогут, то мы тоже никого не пощадим.
Re[20]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 01.04.11 14:26
Оценка:
Здравствуйте, adontz, Вы писали:

A>outer join не имеет большого отношения именно к SQL. Это достаточно понятная процедура над множествами сама по себе.


И как "проблему", о которой вы тут так долго рассказываете, решается в случае с множествами?
Если нам не помогут, то мы тоже никого не пощадим.
Re[21]: SQL(sp + view || Linq)
От: adontz Грузия http://adontz.wordpress.com/
Дата: 01.04.11 14:29
Оценка:
Здравствуйте, IT, Вы писали:

A>>Пример чего, right outer join? Вот есть right join, как сказать что связываемые поля должны (или не должны) быть nullable.

IT>Зачем так много говорить, напиши код и мы его разберём.

Игорь, зачем тебе код, что тебе не ясно? В результате исполнения right join некоторые столбцы в некоторых строках могут быть равны NULL. Тебе нужен код подтверждающий это утверждение?

A>>Для value типов это весьма некорректно.

IT>Да ладно.

Ну если должно быть null, а получилось 0, то да, потому что, очевидно, null != 0.
A journey of a thousand miles must begin with a single step © Lau Tsu
Re[21]: SQL(sp + view || Linq)
От: adontz Грузия http://adontz.wordpress.com/
Дата: 01.04.11 14:30
Оценка:
Здравствуйте, IT, Вы писали:

A>>outer join не имеет большого отношения именно к SQL. Это достаточно понятная процедура над множествами сама по себе.

IT>И как "проблему", о которой вы тут так долго рассказываете, решается в случае с множествами?

Там проблемы нет, поэтому никак.
A journey of a thousand miles must begin with a single step © Lau Tsu
Re[22]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 01.04.11 14:32
Оценка:
Здравствуйте, adontz, Вы писали:

A>>>Пример чего, right outer join? Вот есть right join, как сказать что связываемые поля должны (или не должны) быть nullable.

IT>>Зачем так много говорить, напиши код и мы его разберём.
A>Игорь, зачем тебе код, что тебе не ясно? В результате исполнения right join некоторые столбцы в некоторых строках могут быть равны NULL. Тебе нужен код подтверждающий это утверждение?

Рома, ты не рассуждай, а напиши пример и всё сразу станет ясно. Зачем теоретизировать, если всё легко можно проверить и продемонстрировать на практике.

A>>>Для value типов это весьма некорректно.

IT>>Да ладно.
A>Ну если должно быть null, а получилось 0, то да, потому что, очевидно, null != 0.

Давай код, без кода я не понимаю о чём ты.
Если нам не помогут, то мы тоже никого не пощадим.
Re[22]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 01.04.11 14:34
Оценка:
Здравствуйте, adontz, Вы писали:

A>>>outer join не имеет большого отношения именно к SQL. Это достаточно понятная процедура над множествами сама по себе.

IT>>И как "проблему", о которой вы тут так долго рассказываете, решается в случае с множествами?
A>Там проблемы нет, поэтому никак.

Ты хочешь сказать, что у одного и того же Linq запроса, но для разных типов источника будет разная семантика?
Если нам не помогут, то мы тоже никого не пощадим.
Re[22]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 01.04.11 14:46
Оценка:
Здравствуйте, adontz, Вы писали:

A>>>outer join не имеет большого отношения именно к SQL. Это достаточно понятная процедура над множествами сама по себе.

IT>>И как "проблему", о которой вы тут так долго рассказываете, решается в случае с множествами?
A>Там проблемы нет, поэтому никак.

Уверен?
Если нам не помогут, то мы тоже никого не пощадим.
Re[23]: SQL(sp + view || Linq)
От: adontz Грузия http://adontz.wordpress.com/
Дата: 01.04.11 14:47
Оценка:
Здравствуйте, IT, Вы писали:

IT>Ты хочешь сказать, что у одного и того же Linq запроса, но для разных типов источника будет разная семантика?


Нет, я о другом говорил, но и это тоже верно.
CREATE TABLE A
(
  [ID] INT IDENTITY PRIMARY KEY NOT NULL,
  [Length] INT NOT NULL
)

CREATE TABLE B
(
  [ID] INT IDENTITY PRIMARY KEY NOT NULL,
  [Weight] INT NOT NULL
)

SELECT
  [A].[Length],
  [B].[Weight]
FROM
  [A]
RIGHT JOIN
  [B] ON [B].[ID] = [A].[ID]


Очевидно что
1) Weight в выборке может быть NULL, хотя столбец Weight в таблице B помечен NOT NULL.
2) Может ли Length быть NULL зависит от структуры таблицы, а не от запроса.

Со второй проблемой можно более или менее разобраться при генерации Linq обёртки для базы данных. Первая проблема существенно сложнее. Скажем следующий запрос тоже содержит RIGHT JOIN, но Weight не может быть NULL.
SELECT
  [A].[Length],
  ISNULL([B].[Weight], 0) AS [Weight]
FROM
  [A]
RIGHT JOIN
  [B] ON [B].[ID] = [A].[ID]

Ну и ещё запрос для поражения психики
SELECT
  [A].[Length],
  [B].[Weight]
FROM
  [A]
RIGHT JOIN
  [B] ON [B].[ID] = [A].[ID]
WHERE
  [B].[Weight] IS NOT NULL
A journey of a thousand miles must begin with a single step © Lau Tsu
Re[24]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 01.04.11 14:54
Оценка:
Здравствуйте, adontz, Вы писали:

IT>>Ты хочешь сказать, что у одного и того же Linq запроса, но для разных типов источника будет разная семантика?

A>Нет, я о другом говорил, но и это тоже верно.



A>
A>SELECT
A>  [A].[Length],
A>  [B].[Weight]
A>FROM
A>  [A]
A>RIGHT JOIN
A>  [B] ON [B].[ID] = [A].[ID]
A>


A>Очевидно что

A>1) Weight в выборке может быть NULL, хотя столбец Weight в таблице B помечен NOT NULL.

Запиши теперь соответствующее выражение на Linq.
Если нам не помогут, то мы тоже никого не пощадим.
Re[25]: SQL(sp + view || Linq)
От: adontz Грузия http://adontz.wordpress.com/
Дата: 01.04.11 14:56
Оценка:
Здравствуйте, IT, Вы писали:

A>>1) Weight в выборке может быть NULL, хотя столбец Weight в таблице B помечен NOT NULL.

IT>Запиши теперь соответствующее выражение на Linq.

А причём тут выражение? Речь об анонимном типе который будет использоваться для представления столбца результата.
A journey of a thousand miles must begin with a single step © Lau Tsu
Re[26]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 01.04.11 15:10
Оценка:
Здравствуйте, adontz, Вы писали:

A>>>1) Weight в выборке может быть NULL, хотя столбец Weight в таблице B помечен NOT NULL.

IT>>Запиши теперь соответствующее выражение на Linq.
A>А причём тут выражение? Речь об анонимном типе который будет использоваться для представления столбца результата.

Ну так запиши его.
Если нам не помогут, то мы тоже никого не пощадим.
Re[27]: SQL(sp + view || Linq)
От: adontz Грузия http://adontz.wordpress.com/
Дата: 01.04.11 15:20
Оценка:
Здравствуйте, IT, Вы писали:

A>>>>1) Weight в выборке может быть NULL, хотя столбец Weight в таблице B помечен NOT NULL.

IT>>>Запиши теперь соответствующее выражение на Linq.
A>>А причём тут выражение? Речь об анонимном типе который будет использоваться для представления столбца результата.
IT>Ну так запиши его.

Ты хочешь всё свести к DefaultIfEmpty?
A journey of a thousand miles must begin with a single step © Lau Tsu
Re[28]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 01.04.11 15:49
Оценка:
Здравствуйте, adontz, Вы писали:

A>Ты хочешь всё свести к DefaultIfEmpty?


Я хочу всё свести к NullReferenceException.
Если нам не помогут, то мы тоже никого не пощадим.
Re[29]: SQL(sp + view || Linq)
От: adontz Грузия http://adontz.wordpress.com/
Дата: 01.04.11 15:52
Оценка:
Здравствуйте, IT, Вы писали:

A>>Ты хочешь всё свести к DefaultIfEmpty?

IT>Я хочу всё свести к NullReferenceException.

От встроенного в компилятор стредства ожидается статический анализ совместимости типов.
A journey of a thousand miles must begin with a single step © Lau Tsu
Re[30]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 01.04.11 15:57
Оценка:
Здравствуйте, adontz, Вы писали:

A>>>Ты хочешь всё свести к DefaultIfEmpty?

IT>>Я хочу всё свести к NullReferenceException.
A>От встроенного в компилятор стредства ожидается статический анализ совместимости типов.

Я тебя ещё раз прошу не теоретизировать, а написать код и тогда сразу будет видно, что ожидается от компилятора.
Если нам не помогут, то мы тоже никого не пощадим.
Re[31]: SQL(sp + view || Linq)
От: adontz Грузия http://adontz.wordpress.com/
Дата: 01.04.11 16:17
Оценка:
Здравствуйте, IT, Вы писали:

A>>>>Ты хочешь всё свести к DefaultIfEmpty?

IT>>>Я хочу всё свести к NullReferenceException.
A>>От встроенного в компилятор стредства ожидается статический анализ совместимости типов.
IT>Я тебя ещё раз прошу не теоретизировать, а написать код и тогда сразу будет видно, что ожидается от компилятора.

Я не могут написать код, по которому это было бы видно. Если можешь, продемонстрируй.
A journey of a thousand miles must begin with a single step © Lau Tsu
Re[32]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 01.04.11 16:28
Оценка:
Здравствуйте, adontz, Вы писали:

IT>>Я тебя ещё раз прошу не теоретизировать, а написать код и тогда сразу будет видно, что ожидается от компилятора.

A>Я не могут написать код, по которому это было бы видно. Если можешь, продемонстрируй.

А что мы тогда здесь обсуждаем?

Давай ещё раз сначала. У вас с Alexander Polyakov есть претензии к Linq 2 SQL в части неверного поведения в случае outer join. Вы можете привести код (Linq выражение), демонстрирующий такое поведение?
Если нам не помогут, то мы тоже никого не пощадим.
Re[33]: SQL(sp + view || Linq)
От: adontz Грузия http://adontz.wordpress.com/
Дата: 01.04.11 16:34
Оценка:
Здравствуйте, IT, Вы писали:

IT>>>Я тебя ещё раз прошу не теоретизировать, а написать код и тогда сразу будет видно, что ожидается от компилятора.

A>>Я не могут написать код, по которому это было бы видно. Если можешь, продемонстрируй.
IT> А что мы тогда здесь обсуждаем?
IT>Давай ещё раз сначала. У вас с Alexander Polyakov есть претензии к Linq 2 SQL в части неверного поведения в случае outer join. Вы можете привести код (Linq выражение), демонстрирующий такое поведение?

Игорь, ну зачем ты переиначиваешь слова? Некрасиво с твоей стороны.

Код тебе привели давным давно
http://www.rsdn.ru/forum/design/4217197.1.aspx
Автор: Alexander Polyakov
Дата: 31.03.11

но ты предпочёл заняться ручным приведением типов
http://www.rsdn.ru/forum/design/4218198.1.aspx
Автор: IT
Дата: 01.04.11

вместо того чтобы признать, что вывод nullable типов хромает.
A journey of a thousand miles must begin with a single step © Lau Tsu
Re[34]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 01.04.11 17:15
Оценка:
Здравствуйте, adontz, Вы писали:

IT>>Давай ещё раз сначала. У вас с Alexander Polyakov есть претензии к Linq 2 SQL в части неверного поведения в случае outer join. Вы можете привести код (Linq выражение), демонстрирующий такое поведение?

A>Игорь, ну зачем ты переиначиваешь слова? Некрасиво с твоей стороны.
A>Код тебе привели давным давно
A>http://www.rsdn.ru/forum/design/4217197.1.aspx
Автор: Alexander Polyakov
Дата: 31.03.11


Это не код, это псевдо код, который в C# не компилируется.

A>но ты предпочёл заняться ручным приведением типов

A>http://www.rsdn.ru/forum/design/4218198.1.aspx
Автор: IT
Дата: 01.04.11

A>вместо того чтобы признать, что вывод nullable типов хромает.

Я тебе привёл пример правильного подхода, такого каким он должен быть. Вот если бы ты сам потрудился всё же написать рабочий код, то смог бы в этом убедиться. Но вместо этого ты здесь вторые сутки рассуждаешь о несуществующей проблеме. Если проблема есть в коде, то приведи этот код, в чём проблема?
Если нам не помогут, то мы тоже никого не пощадим.
Re[35]: SQL(sp + view || Linq)
От: adontz Грузия http://adontz.wordpress.com/
Дата: 01.04.11 19:05
Оценка:
Здравствуйте, IT, Вы писали:

IT>Я тебе привёл пример правильного подхода, такого каким он должен быть.


То есть вручную указывать типы это правильно?
A journey of a thousand miles must begin with a single step © Lau Tsu
Re[36]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 01.04.11 19:48
Оценка:
Здравствуйте, adontz, Вы писали:

IT>>Я тебе привёл пример правильного подхода, такого каким он должен быть.

A>То есть вручную указывать типы это правильно?

Правильно проверять на null, а что там куда указывать дело десятое. Ты бы сам попробовал рабочий код написать и все вопросы сразу бы отпали.
Если нам не помогут, то мы тоже никого не пощадим.
Re[17]: SQL(sp + view || Linq)
От: Alexander Polyakov  
Дата: 01.04.11 20:58
Оценка:
Здравствуйте, IT, Вы писали:

AP>>Смотри, если переписать твой пример вот так:

AP>>db.Table.Select(t => new { Field1 = t.Field1, Field2 = new int?() }).Union(
AP>>db.Table.Select(t => new { Field1 = new int?(), Field2 = t.Field2 }))
AP>>.Select(t => new Table { Field1 = t.Field1, Field2 = t.Field2 })
AP>>то будет ошибка компиляции в третьей строчке (уже в текущей версии C#).
IT>Ошибка будет раньше.
Да, надо немного поправить:
db.Table.Select(t => new { Field1 = (int?)t.Field1, Field2 = (int?)null }).Union(
db.Table.Select(t => new { Field1 = (int?)null, Field2 = (int?)t.Field2 }))
.Select(t => new Table { Field1 = t.Field1, Field2 = t.Field2 })

Теперь ошибка в третьей строчке. Я это к чему, если в твоем примере пользоваться анонимным классом, то никакой проблемы нет -- поле анонимного класса надо делать nullable иначе компилятор не пропускает (а ты писал о какой-то проблеме). Почему анонимные классы лучше демонстрируют предмет обсуждения? Потому что их поля не инициализируются автоматически каким-либо значением, программист должен прописать инициализацию всех полей явно. В твоей же первоначальной записи null-ов вообще нет, там есть всего лишь неявная инициализация полей именованного класса, зачем ты привел тот пример мне так и не ясно, в нем нет демонстрации какой-либо проблемы.

IT>Это всё решается.

IT>
IT>from aaa in Aaa
IT>left join bbb in Bbb
IT>on aaa.A001 equals bbb.B001
IT>select new
IT>{
IT>    // если тебе нужен весь объект, то он будет null
IT>    bbb,
IT>    // если отдельное поле
IT>    B001 = bbb == null ? (int?)null : bbb.B001,
IT>    B002 = bbb == null ? (int?)null : bbb.B002
IT>};
IT>

Нет, это не решение. Ты не понимаешь проблемы, и приводишь “решение”, не имеющие отношение к задаче. Задача в том, чтобы компилятор контролировал правильность nullability полей. В твоей записи со стороны компилятора контроля nullability нет.

Вот эта запись корректна?
from aaa in Aaa
left join bbb in Bbb
on aaa.A001 equals bbb.B001
select new
{
    bbb.B001,
    bbb.B002
};

Если да, то, какого типа поля B001 и B002 анонимного класса? Прошу написать явно ответ на этот вопрос. Думаю, что после ответа пойдет более конструктивный разговор.
Re[37]: SQL(sp + view || Linq)
От: Alexander Polyakov  
Дата: 01.04.11 21:17
Оценка:
Здравствуйте, IT, Вы писали:

IT>Правильно проверять на null ...

Мы обсуждаем работу с SQL-ыми базами, ведь так? А про SQL-ые базы не слышно было, чтобы в них целые строки были null-ами. Отдельные поля, да, могут быть NULL-ами, но целые строки, нет, такого даже понятия нет. Таким образом, изначально null-строк у нас нет, а ты предлагаешь писать проверки на null-строки … откуда же они могут появиться … так оказывается из-за кривизны нашего языка запросов. Костыли, батенька, костыли.
Re[38]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 01.04.11 21:41
Оценка:
Здравствуйте, Alexander Polyakov, Вы писали:

IT>>Правильно проверять на null ...

AP>Мы обсуждаем работу с SQL-ыми базами, ведь так?

Мы обсуждаем работу с SQL-ыми базами в контексте Linq.

AP>А про SQL-ые базы не слышно было, чтобы в них целые строки были null-ами. Отдельные поля, да, могут быть NULL-ами, но целые строки, нет, такого даже понятия нет. Таким образом, изначально null-строк у нас нет, а ты предлагаешь писать проверки на null-строки … откуда же они могут появиться … так оказывается из-за кривизны нашего языка запросов. Костыли, батенька, костыли.


Я предлагаю проверки не на null-строки, а проверку на null-объекты. В точности как этого требуют правила используемого тобой языка. Напиши такой же точно запрос, точнее даже используй тот же самый запрос с другим источником данных, пусть это будут, например, массивы, а не таблицы и ты тут же получишь в райнтайм ошибку выполнения. Ты тоже в этом случае будешь жаловаться на кривизну языка запросов?
Если нам не помогут, то мы тоже никого не пощадим.
Re[18]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 01.04.11 21:51
Оценка:
Здравствуйте, Alexander Polyakov, Вы писали:

AP>
AP>db.Table.Select(t => new { Field1 = (int?)t.Field1, Field2 = (int?)null }).Union(
AP>db.Table.Select(t => new { Field1 = (int?)null, Field2 = (int?)t.Field2 }))
AP>.Select(t => new Table { Field1 = t.Field1, Field2 = t.Field2 })
AP>

AP>Теперь ошибка в третьей строчке.

Естественно, тут же написан бред.

AP>Я это к чему, если в твоем примере пользоваться анонимным классом, то никакой проблемы нет -- поле анонимного класса надо делать nullable иначе компилятор не пропускает (а ты писал о какой-то проблеме). Почему анонимные классы лучше демонстрируют предмет обсуждения? Потому что их поля не инициализируются автоматически каким-либо значением, программист должен прописать инициализацию всех полей явно. В твоей же первоначальной записи null-ов вообще нет, там есть всего лишь неявная инициализация полей именованного класса, зачем ты привел тот пример мне так и не ясно, в нем нет демонстрации какой-либо проблемы.


Так никакой проблемы нет вообще. Это вы с Ромой её себе придумали.

AP>Нет, это не решение. Ты не понимаешь проблемы, и приводишь “решение”, не имеющие отношение к задаче. Задача в том, чтобы компилятор контролировал правильность nullability полей. В твоей записи со стороны компилятора контроля nullability нет.


Что за чушь

AP>Вот эта запись корректна?

AP>
AP>from aaa in Aaa
AP>left join bbb in Bbb
AP>on aaa.A001 equals bbb.B001
AP>select new
AP>{
AP>    bbb.B001,
AP>    bbb.B002
AP>};
AP>

AP>Если да, то, какого типа поля B001 и B002 анонимного класса? Прошу написать явно ответ на этот вопрос. Думаю, что после ответа пойдет более конструктивный разговор.

Эта запись корректна синтаксически. Так же как и корректен синтаксически следующий код:

string s = null;
s.Substring(1);

Но этот код, так же как и приведённый тобой содержит ошибку. Замени Aaa и Bbb в своём коде на массивы и ты получишь NullReferenceException. Почему же ты думаешь, что семантически эквивалентный код должен обрабатываться компилятором по-разному?

Да, SQL прощает некоторые вещи и позволяет упрощать некоторые конструкции, но это плюс SQL, а не минус Linq/C#. Вы же тут почему-то хотите доказать обратное
Если нам не помогут, то мы тоже никого не пощадим.
Re[19]: SQL(sp + view || Linq)
От: Alexander Polyakov  
Дата: 01.04.11 22:15
Оценка:
Здравствуйте, IT, Вы писали:

IT>Так никакой проблемы нет вообще.

Твои слова:

На самом деле это более общая проблема
http://rsdn.ru/forum/design/4217251.1.aspx

Re[19]: SQL(sp + view || Linq)
От: Alexander Polyakov  
Дата: 01.04.11 22:19
Оценка: :)
Здравствуйте, IT, Вы писали:

IT>Да, SQL прощает некоторые вещи и позволяет упрощать некоторые конструкции, но это плюс SQL

Я рад, что ты выводы сделал правильные, хотя детали обсуждаемой проблемы, по-видимому, остались за пределами твоего понимания.
Re[19]: SQL(sp + view || Linq)
От: MozgC США http://nightcoder.livejournal.com
Дата: 02.04.11 11:25
Оценка:
Игорь, я думаю что твои оппоненты имели в виду что-то типа этой проблемы:
http://rsdn.ru/forum/prj.rfd/4209149.flat.aspx
Автор: MozgC
Дата: 25.03.11

Т.е. использование left join делает запись мягко говоря неудобной и заставляет использовать какие-то хаки, чтобы добиться желаемого. Можно ли сделать как-то проще?
Re[20]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 02.04.11 13:52
Оценка:
Здравствуйте, Alexander Polyakov, Вы писали:

AP>Здравствуйте, IT, Вы писали:


IT>>Так никакой проблемы нет вообще.

AP>Твои слова:
AP>

AP>На самом деле это более общая проблема
AP>http://rsdn.ru/forum/design/4217251.1.aspx


Мои, ну и что? Я тебе пытался лишь сказать, что смотреть на мир нужно шире, а не зацикливаться лишь на left join. Но по большому счёту всё это фигня.
Если нам не помогут, то мы тоже никого не пощадим.
Re[20]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 02.04.11 14:04
Оценка:
Здравствуйте, MozgC, Вы писали:

MC>Игорь, я думаю что твои оппоненты имели в виду что-то типа этой проблемы:

MC>http://rsdn.ru/forum/prj.rfd/4209149.flat.aspx
Автор: MozgC
Дата: 25.03.11

MC>Т.е. использование left join делает запись мягко говоря неудобной и заставляет использовать какие-то хаки, чтобы добиться желаемого. Можно ли сделать как-то проще?

Мои оппоненты путают тёплое с мягким, а именно семантику языка с библиотечной реализацией конкретного провайдера. Они приводят логически кривой код, а потом возмущаются, что с ним неудобно работать. Вот такой код не будет работать в linq 2 object:

...
left join t ...
select t.Aaa

Здесь мы в рантайм получим NullReferenceException. Так почему же такой код должен работать так как хотят мои оппоненты в linq 2 sql? Бред ведь. Тут не linq и C# нужно выправлять, а мозги.
Если нам не помогут, то мы тоже никого не пощадим.
Re[20]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 02.04.11 14:05
Оценка:
Здравствуйте, Alexander Polyakov, Вы писали:

IT>>Да, SQL прощает некоторые вещи и позволяет упрощать некоторые конструкции, но это плюс SQL

AP>Я рад, что ты выводы сделал правильные, хотя детали обсуждаемой проблемы, по-видимому, остались за пределами твоего понимания.

Понятно. Когда сказать больше нечего, остаётся только сливать, переключаяь на личность оппонента.
Если нам не помогут, то мы тоже никого не пощадим.
Re[21]: SQL(sp + view || Linq)
От: adontz Грузия http://adontz.wordpress.com/
Дата: 02.04.11 14:11
Оценка:
Здравствуйте, IT, Вы писали:

IT>Здесь мы в рантайм получим NullReferenceException.


Это особенность реализации.

IT>Так почему же такой код должен работать так как хотят мои оппоненты в linq 2 sql?


Вообще-то, если бы код в linq2objects работал возвращая null, я не был бы против. Почему ты решил, что мы хотим разного поведения у разных провайдеров linq? Оно везде неправильное, просто в linq2sql это заметнее.

IT>Бред ведь. Тут не linq и C# нужно выправлять, а мозги.


Игорь, давай без переходов на личности. Кому надо мозги поменять — недостойная тема.
A journey of a thousand miles must begin with a single step © Lau Tsu
Re[22]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 02.04.11 14:19
Оценка:
Здравствуйте, adontz, Вы писали:

IT>>Здесь мы в рантайм получим NullReferenceException.

A>Это особенность реализации.

Особенно реализации чего? Компилятора? Следующий код это тоже особенность реализации? :

string s = null;
s.Substring(1);

IT>>Так почему же такой код должен работать так как хотят мои оппоненты в linq 2 sql?

A>Вообще-то, если бы код в linq2objects работал возвращая null, я не был бы против. Почему ты решил, что мы хотим разного поведения у разных провайдеров linq? Оно везде неправильное, просто в linq2sql это заметнее.


Это просто какой-то капец!

IT>>Бред ведь. Тут не linq и C# нужно выправлять, а мозги.

A>Игорь, давай без переходов на личности. Кому надо мозги поменять — недостойная тема.

Это ты прежде всего своему единомышленнику скажи. Похоже он начал сливать, но втихую слить ему ЧСВ не позволяет и он начал переключаться на личности. Что же касается мозгов, то их действительно периодически приходится подправлять. Ничего необычного и постыдного в этом нет.
Если нам не помогут, то мы тоже никого не пощадим.
Re[21]: SQL(sp + view || Linq)
От: Alexander Polyakov  
Дата: 02.04.11 14:49
Оценка:
Здравствуйте, IT, Вы писали:

IT>Мои, ну и что? Я тебе пытался лишь сказать, что смотреть на мир нужно шире, а не зацикливаться лишь на left join.

Я прекрасно понимаю твои намерения, однако, тебе не удалось показать, что в данном случае проблема шире, чем я ее описываю. Я бы с удовольствием расширил бы взгляд на мир, если бы на то были основания.
Re[23]: SQL(sp + view || Linq)
От: adontz Грузия http://adontz.wordpress.com/
Дата: 02.04.11 14:52
Оценка:
Здравствуйте, IT, Вы писали:

IT>Особенно реализации чего? Компилятора?


Вобщем-то, да.

IT>Следующий код это тоже особенность реализации? :

IT>
IT>string s = null;
IT>s.Substring(1);
IT>


Безусловно. Я не вижу ничего плохого в null.Substring(1) == null. Собственно, это не что-то новое в программировании. Специальная обработка пограничных значений достаточно обычная практика. У нас, например, уже есть разные виды NaN, включая +Infinity и -Infinity. Если +Inf — 1 == +Inf, то что странного в том что null.Substring(1) == null? Компилятору, кстати говоря, было бы очень легко поддерживать такое поведение. Есть оператор ?? для упрощения ручной поддержки. При работе с древовидными структурами вместо null может использоваться другой элемент как я уже описывал в статье
Автор(ы): Роман Акопов
Дата: 22.05.2004
Статья рассказывает об алгоритмах работы с двоичными деревьями поиска и о красно-черных деревьях (КЧД). Производится сравнение скоростных характеристик различных операций для деревьев и массивов. В прилагаемом С++-коде приводится реализация бинарных деревьев поиска и красно-черных деревьев.
.

A>>Вообще-то, если бы код в linq2objects работал возвращая null, я не был бы против. Почему ты решил, что мы хотим разного поведения у разных провайдеров linq? Оно везде неправильное, просто в linq2sql это заметнее.

IT>Это просто какой-то капец!

Да нет, это абсолютно логичное поведение при обработке множеств. Более того, это исторически сложившееся практика, что делает текущее поведение linq ещё более неприемлемым. SELECT NULL + 4 возвращает NULL. Так мы работает с данными. Это логично, это удобно.
То что ты говоришь тоже, по своему, логично, в том смысле что это однообразное поведение. Но это менее удобно, и, к тому же, в области обработки данных уже сложилась другая традиция.

IT>>>Бред ведь. Тут не linq и C# нужно выправлять, а мозги.

A>>Игорь, давай без переходов на личности. Кому надо мозги поменять — недостойная тема.
IT>Это ты прежде всего своему единомышленнику скажи.

Если тебя обидел кто-то другой срываться на мне не надо. Он — Александр, я — Роман. Как "Война и Мир", только человек. Перепутать сложно.

IT>Что же касается мозгов, то их действительно периодически приходится подправлять. Ничего необычного и постыдного в этом нет.


Я думаю, мне нет необходимости объяснять тебе суть формата вежливой дискуссии или напоминать об обязательности соблюдения данного формата при общении, в частности, между нами. Давай сконцентрируемся на профессиональных темах.
A journey of a thousand miles must begin with a single step © Lau Tsu
Re[21]: SQL(sp + view || Linq)
От: Alexander Polyakov  
Дата: 02.04.11 15:05
Оценка:
Здравствуйте, IT, Вы писали:

IT>Но по большому счёту всё это фигня.

Твое поведение странное: сначала ты пишешь, что проблема шире, теперь пишешь, что проблемы вообще нет. Если ее нет, то как она может быть шире той, которую сформулировал я?
Re[24]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 02.04.11 15:11
Оценка:
Здравствуйте, adontz, Вы писали:

A>Безусловно. Я не вижу ничего плохого в null.Substring(1) == null.


Тогда тебе нужно обсуждать C# в целом, а не linq в частности.
Если нам не помогут, то мы тоже никого не пощадим.
Re[22]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 02.04.11 15:12
Оценка:
Здравствуйте, Alexander Polyakov, Вы писали:

IT>>Но по большому счёту всё это фигня.

AP>Твое поведение странное: сначала ты пишешь, что проблема шире, теперь пишешь, что проблемы вообще нет. Если ее нет, то как она может быть шире той, которую сформулировал я?

Давай я перефразирую, чтобы тебе было понятней. Проблемка, малюсенькая такая проблемочка, которую в принципе даже не видно в микроскоп, немного шире, чем ты думаешь. Так устроит?
Если нам не помогут, то мы тоже никого не пощадим.
Re[25]: SQL(sp + view || Linq)
От: adontz Грузия http://adontz.wordpress.com/
Дата: 02.04.11 15:18
Оценка:
Здравствуйте, IT, Вы писали:

A>>Безусловно. Я не вижу ничего плохого в null.Substring(1) == null.

IT>Тогда тебе нужно обсуждать C# в целом, а не linq в частности.

Linq — это ведь не просто библиотека, синтаксис был существенно расширен ради linq, компилятор переделан. Так что обсуждать, почему не добавили всё необходимое для обработки запросов, в рамках обсуждения linq ИМХО вполне примлемо. Хотя если ты настаиваешь, можем завершить обсуждение вопроса с формулировкой "too epic subject".
A journey of a thousand miles must begin with a single step © Lau Tsu
Re[21]: SQL(sp + view || Linq)
От: MozgC США http://nightcoder.livejournal.com
Дата: 02.04.11 15:41
Оценка:
Здравствуйте, IT, Вы писали:

MC>>Игорь, я думаю что твои оппоненты имели в виду что-то типа этой проблемы:

MC>>http://rsdn.ru/forum/prj.rfd/4209149.flat.aspx
Автор: MozgC
Дата: 25.03.11

MC>>Т.е. использование left join делает запись мягко говоря неудобной и заставляет использовать какие-то хаки, чтобы добиться желаемого. Можно ли сделать как-то проще?

IT>Мои оппоненты путают тёплое с мягким, а именно семантику языка с библиотечной реализацией конкретного провайдера. Они приводят логически кривой код, а потом возмущаются, что с ним неудобно работать. Вот такой код не будет работать в linq 2 object:


IT>
IT>...
IT>left join t ...
IT>select t.Aaa
IT>

IT>Здесь мы в рантайм получим NullReferenceException. Так почему же такой код должен работать так как хотят мои оппоненты в linq 2 sql? Бред ведь. Тут не linq и C# нужно выправлять, а мозги.

А если эгоистично вернуться к моему вопросу на который я дал ссылку, ты не мог бы на него ответить? Или проще никак не сделать?
Re[26]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 02.04.11 15:56
Оценка:
Здравствуйте, adontz, Вы писали:

A>>>Безусловно. Я не вижу ничего плохого в null.Substring(1) == null.

IT>>Тогда тебе нужно обсуждать C# в целом, а не linq в частности.

A>Linq — это ведь не просто библиотека, синтаксис был существенно расширен ради linq, компилятор переделан. Так что обсуждать, почему не добавили всё необходимое для обработки запросов, в рамках обсуждения linq ИМХО вполне примлемо. Хотя если ты настаиваешь, можем завершить обсуждение вопроса с формулировкой "too epic subject".


Компилятор был именно расширен. Ты же предлагаешь изменить текущее поведение компилятора. Такие вещи в принципе можно делать, но только не в C#, а сами знаете в чём. Кстати, Влад недавно добавил в сами знаете во что оператор '?.' (а может '.?'), довольно удобная штука, позволяющая записывать выражения типа a?.b?.c?.d. Но это всё всё равно сахар.
Если нам не помогут, то мы тоже никого не пощадим.
Re[23]: SQL(sp + view || Linq)
От: Alexander Polyakov  
Дата: 02.04.11 16:30
Оценка:
Здравствуйте, IT, Вы писали:

IT>... немного шире, чем ты думаешь ...

Так покажи это. В твоем примере с Union нет даже малюсенькой проблемы.
Re[27]: SQL(sp + view || Linq)
От: adontz Грузия http://adontz.wordpress.com/
Дата: 02.04.11 16:39
Оценка:
Здравствуйте, IT, Вы писали:

A>>Linq — это ведь не просто библиотека, синтаксис был существенно расширен ради linq, компилятор переделан. Так что обсуждать, почему не добавили всё необходимое для обработки запросов, в рамках обсуждения linq ИМХО вполне примлемо. Хотя если ты настаиваешь, можем завершить обсуждение вопроса с формулировкой "too epic subject".

IT>Компилятор был именно расширен. Ты же предлагаешь изменить текущее поведение компилятора.

Расширили бы компилятор этим вашим ?. или .? А так получается недоделка.
A journey of a thousand miles must begin with a single step © Lau Tsu
Re[28]: SQL(sp + view || Linq)
От: IT Россия linq2db.com
Дата: 02.04.11 17:38
Оценка:
Здравствуйте, adontz, Вы писали:

A>Расширили бы компилятор этим вашим ?. или .? А так получается недоделка.


Это к Хейльсбергу.
Если нам не помогут, то мы тоже никого не пощадим.
Re[29]: SQL(sp + view || Linq)
От: adontz Грузия http://adontz.wordpress.com/
Дата: 02.04.11 17:40
Оценка:
Здравствуйте, IT, Вы писали:

A>>Расширили бы компилятор этим вашим ?. или .? А так получается недоделка.

IT>Это к Хейльсбергу.

Да, я в курсе
A journey of a thousand miles must begin with a single step © Lau Tsu
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.