Deutsch
Germany.ruФорумы → Архив Досок→ Программирование

Две таблицы...

614  1 2 все
Murr патриот08.06.15 15:16
Murr
08.06.15 15:16 
Дано - две таблицы <DataTable> АА & BB - заполняемые из физически разных оракловских баз...
Как проще всего написать эквивалент <SELECT * FROM AA A WHERE A.NO IN (SELECT NO FROM BB B)>
в С#?
Пока Я их предварительно отсортировал с делал все в один проход - все быстро, но читать тяжело.
Хочется чтобы было так же быстро, но выглядело по-проще...
#1 
NightWatch коренной житель08.06.15 16:08
NightWatch
NEW 08.06.15 16:08 
в ответ Murr 08.06.15 15:16
var query = from aa_row in AA
join bb_row in BB on aa_row.NO equals bb_row.NO
select aa_row;


#2 
Murr патриот08.06.15 17:58
Murr
NEW 08.06.15 17:58 
в ответ NightWatch 08.06.15 16:08
Это красиво, но будет много медленнее.
Хотя... надо посмотреть - может и достаточно...
<Thank>
#3 
AlexNek патриот08.06.15 23:58
AlexNek
NEW 08.06.15 23:58 
в ответ Murr 08.06.15 17:58
В ответ на:
Это красиво, но будет много медленнее

Вам красиво или быстро
Вообще то можно и самому Linq провайдер сделать.
Хотя на прошлом проекте все Linq запросы выбросили, надоело сравнивать с оптимальным кодом.
#4 
Murr патриот09.06.15 08:15
Murr
NEW 09.06.15 08:15 
в ответ AlexNek 08.06.15 23:58
Нам таки, как обычно, быструю красоту...
#5 
web-programmist Web-Developer09.06.15 11:20
web-programmist
NEW 09.06.15 11:20 
в ответ Murr 08.06.15 17:58
А кто мешает сделать запрос и функцию чтения "пачками" ? (limit..)
Более 500 каналов !
#6 
Murr патриот09.06.15 11:57
Murr
NEW 09.06.15 11:57 
в ответ web-programmist 09.06.15 11:20
А кто мешает сделать запрос и функцию чтения "пачками" ? (limit..)
-----
Не понял вопроса. Поясни что имелось в виду.
#7 
Murr патриот12.06.15 13:03
Murr
NEW 12.06.15 13:03 
в ответ NightWatch 08.06.15 16:08
Попробовал;
            var query = from current in pCurrent.Rows.Cast<Rows.UnfinishedOrders>()
join delivery in deliveryStatus.Cast<Rows.DeliveryStatus>() on current.OrderNo equals delivery.OrderNo
select current;
int count = query.Count();


            Unable to cast - - of type 'System.Data.DataRow' to type 'UnfinishedOrders'.


При этом <public static implicit operator UnfinishedOrders(DataRow)> - имеется.
<LINQ> - хорошо, но надо регулярно пользоваться... забыл уже детали...
Эээ... этот кусок сейчас получается одним из тормозов - выборка из базы делается быстрее, чем двойной цикл с проверкой совпадений...
Придется делать некрасивый и малопонятный код прохождения двух сортированных таблиц...

#8 
Murr патриот12.06.15 13:09
Murr
NEW 12.06.15 13:09 
в ответ Murr 12.06.15 13:03
Поправил на:
            var query = from current in pCurrent.Rows.Cast<DataRow>()
join delivery in deliveryStatus.Cast<Rows.DeliveryStatus>() on current["orderNo"] equals delivery.OrderNo
select current;


и получил ноль отобранных на выходе...
Правда, надо признать, ноль был получен почти мгновенно...

#9 
NightWatch коренной житель12.06.15 15:15
NightWatch
NEW 12.06.15 15:15 
в ответ Murr 12.06.15 13:03
В ответ на:
При этом <public static implicit operator UnfinishedOrders(DataRow)> - имеется.

explicit должен быть.
#10 
NightWatch коренной житель12.06.15 15:18
NightWatch
NEW 12.06.15 15:18 
в ответ Murr 12.06.15 13:09
В ответ на:
current["orderNo"]
delivery.OrderNo
Какие типы?
#11 
Murr патриот12.06.15 15:30
Murr
NEW 12.06.15 15:30 
в ответ NightWatch 12.06.15 15:15
Почему <explicit>? У меня никакой потенциальной потери данных не имеется.
#12 
Murr патриот12.06.15 15:33
Murr
NEW 12.06.15 15:33 
в ответ NightWatch 12.06.15 15:18
Или <int> и <int>
Или <decimal> и <decimal>
Есть, конечно шанс на <int> и <decimal>, но маловероятно...
Собственно, для отсутствия данных проблем и писались <Rows.Сomething>.
#13 
NightWatch коренной житель12.06.15 15:34
NightWatch
NEW 12.06.15 15:34 
в ответ Murr 12.06.15 15:30
Это я сморозил.
#14 
Murr патриот12.06.15 15:59
Murr
NEW 12.06.15 15:59 
в ответ NightWatch 12.06.15 15:34
А может и нет - надо смотреть как они там кастинг имплементировали - может именно <explicit> нужен.
#15 
NightWatch коренной житель12.06.15 16:23
NightWatch
NEW 12.06.15 16:23 
в ответ Murr 12.06.15 13:03, Последний раз изменено 12.06.15 17:25 (NightWatch)
Э-э-э, тут дело в раннем связывании. Методы преобразования типов должны быть известны и связываются во время компиляции. Так что Enumerable.Cast "не знает" о существовании пользовательского метода преобразования.
Обходится либо так, как ты сделал, либо
pCurrent.Rows.Cast<DataRow>().Select(r => (Rows.UnfinishedOrders)r)

наверное экономичнее будет приведение в селектор ключа запихнуть:

var query = from current in pCurrent.Rows.Cast<DataRow>()
join delivery in deliveryStatus.Cast<Rows.DeliveryStatus>() on ((Rows.UnfinishedOrders)current).OrderNo equals delivery.OrderNo
select current;


#16 
NightWatch коренной житель12.06.15 16:43
NightWatch
NEW 12.06.15 16:43 
в ответ Murr 12.06.15 15:33, Последний раз изменено 12.06.15 16:43 (NightWatch)
В ответ на:
Или <int> и <int>
Или <decimal> и <decimal>
Есть, конечно шанс на <int> и <decimal>, но маловероятно...
Отчего такая неопределенность? А может там тогда вообще string или Point?
#17 
NightWatch коренной житель12.06.15 16:49
NightWatch
NEW 12.06.15 16:49 
в ответ Murr 12.06.15 15:59
В ответ на:
А может и нет - надо смотреть как они там кастинг имплементировали - может именно <explicit> нужен.
Не. Если есть implicit operator, то и явное и неявное преобразование работает. Explicit operator разрешает только явное преобразование.
#18 
Murr патриот12.06.15 17:10
Murr
NEW 12.06.15 17:10 
в ответ NightWatch 12.06.15 16:23
Чуток зверею...
<LINQ> - 0:00.55 sec
двойной цикл - 1:32.84
остался сложный вопрос - запихнуть результат <Select>а в <DataTable>
#19 
Murr патриот12.06.15 17:13
Murr
NEW 12.06.15 17:13 
в ответ NightWatch 12.06.15 16:43
Отчего такая неопределенность?
-----
От того, что запрос к базе возвращает что-то... по идее должно быть целое, но по факту - <decimal>.
<String>ом мучался предыдущий прогер с известным результатом.
#20 
NightWatch коренной житель12.06.15 17:33
NightWatch
NEW 12.06.15 17:33 
в ответ Murr 12.06.15 17:10
Ну, если результат селекта - IEnumerable<DataRow>, то в лоб напрашивается цикл, в котором импортируются строки: table.ImportRow(r);
#21 
Murr патриот12.06.15 17:40
Murr
NEW 12.06.15 17:40 
в ответ NightWatch 12.06.15 17:33
Насколько Я понимаю - результат <Select>а <IEnumerable<Rows.UnfinishedOrders>>
И дизайнено так, что бы до внутреннего <DataRow> добраться было сложно...
Хотя... может ну его, этот <DataTable>?
Что меня смущает - есть такая радость <CopyToDataTable()>
С <DataRow[ ]> - работает на раз... а вот с результатом <Select>а - полный облом.
#22 
NightWatch коренной житель12.06.15 17:44
NightWatch
NEW 12.06.15 17:44 
в ответ Murr 12.06.15 17:40, Последний раз изменено 12.06.15 17:44 (NightWatch)
Приведи актуальный запрос. Потому что результатом

var query = from current in pCurrent.Rows.Cast<DataRow>()
join delivery in deliveryStatus.Cast<Rows.DeliveryStatus>() on current["orderNo"] equals delivery.OrderNo
select current;


будет IEnumerable<DataRow>.

#23 
NightWatch коренной житель12.06.15 17:52
NightWatch
NEW 12.06.15 17:52 
в ответ Murr 12.06.15 17:40
В ответ на:
Что меня смущает - есть такая радость <CopyToDataTable()>
Тот же цикл, но с кучей проверок.
#24 
Murr патриот12.06.15 18:21
Murr
NEW 12.06.15 18:21 
в ответ NightWatch 12.06.15 17:44
будет IEnumerable<DataRow>.
-----
Да, но с пустым результатом.
Проблема - current["orderNo"] equals delivery.OrderNo - <decimal> <int>.
Актуальный код:
            var query1 = from current in pCurrent.Rows.Cast<DataRow>().Select(r => (Rows.UnfinishedOrders)r)
join delivery in deliveryStatus.Cast<Rows.DeliveryStatus>() on current.OrderNo equals delivery.OrderNo
where delivery.DeliveryStatusS == TDeliveryStatus.NotDelivered
select current;
var query2 = from current in pCurrent.Rows.Cast<DataRow>().Select(r => (Rows.UnfinishedOrders)r)
join delivery in deliveryStatus.Cast<Rows.DeliveryStatus>() on current.OrderNo equals delivery.OrderNo
where delivery.DeliveryStatusS == TDeliveryStatus.PartiallyDelivered
select current;
foreach (Rows.UnfinishedOrders row in query1)
{
row.DeliveryStatus = TDeliveryStatus.NotDelivered;
}
foreach (Rows.UnfinishedOrders row in query2)
{
row.DeliveryStatus = TDeliveryStatus.PartiallyDelivered;
}


дальше нужно слияние и перегонка в <DataTable>. Ну либо переработка (ее мне сейчас делать не хочется) остального кода.
Хммм... там, по имеющемуся коду, еще одно поле требует заполнения, но за все время Я не видел, чтобы значения отличались.

<--- nobody harmed in this action -->
#25 
NightWatch коренной житель12.06.15 18:31
NightWatch
NEW 12.06.15 18:31 
в ответ Murr 12.06.15 18:21
В ответ на:
Да, но с пустым результатом.
Проблема - current["orderNo"] equals delivery.OrderNo - <decimal> <int>.
(int)(decimal)current["orderNo"] equals delivery.OrderNo
#26 
Murr патриот15.06.15 13:52
Murr
NEW 15.06.15 13:52 
в ответ NightWatch 12.06.15 18:31
Это надо будет еще тестить.
Пока другая задница вылезла. Хитрая такая...
Если делать заполнение таблицы из какого-то стандартного источника - <DataReader> и Ко - то в <DataTable> помещаются данные и структура этих данных.
А вот если заполнять таблицу через <ImportRow()>, то структуры на месте не имеется...
Пошел искать где допустимо пользовать <Clone()>...
#27 
Murr патриот15.06.15 16:39
Murr
NEW 15.06.15 16:39 
в ответ Murr 15.06.15 13:52
Очередная веселая нособойка - статический конструктор С#-обьекта (<VS2012>) из <VB> <VS2010> - не вызывается...
Или есть какие-то настройки на совместимость?
#28 
1 2 все