Этот баннер — требование Роскомнадзора для исполнения 152 ФЗ.
«На сайте осуществляется обработка файлов cookie, необходимых для работы сайта, а также для анализа использования сайта и улучшения предоставляемых сервисов с использованием метрической программы Яндекс.Метрика. Продолжая использовать сайт, вы даёте согласие с использованием данных технологий».
Политика конфиденциальности
|
|
|
То ли сервер глюкавый, то ли руки кривые... HELP!
|
|||
|---|---|---|---|
|
#18+
Имеется такое вот чудо ... мысли. CREATE PROCEDURE ЖурналДвижений (@КодФирмы int =4)as begin declare @ЖурналРасходов table (КодДвижения int , КодПрихода int , ОстатокПрихода decimal (9, 3) , КоличествоРасхода decimal (9, 3) , ФлагПартии bit ) declare @КодДвижения int , @КоличествоРасхода decimal (9, 3) , @ФлагПартии bit declare ПереченьРасходов CURSOR FOR select КодДвижения, КоличествоРасхода=Количество, ФлагПартии from dbo.ДвиженияПоКорреспонденту(null, @КодФирмы, null, null) where ТипДвижения<>'Приход' open ПереченьРасходов WHILE @@FETCH_STATUS = 0 begin fetch next from ПереченьРасходов into @КодДвижения , @КоличествоРасхода , @ФлагПартии insert into @ЖурналРасходов select * from dbo.СписаниеFIFOРасходы(@КодДвижения) end select * from @ЖурналРасходов end Общий смысл в том, что на каждую запись во входном наборе данных функцией СписаниеFIFOРасходы() возвращаеся несколько записей. Обе, использующиеся UDF работают как часы (китайские само собой ). И я не буду спрашивать почему оно не работает, потому что оно работает и очень хорошо... Но только один раз. Т.е на Open или Debug в QA возвращается нормальный набор записей. А exec ЖурналДвижений default первый раз отрабатывает нормально, а потом возвращает пустой набор . На клиенте (MSAccess2000 adp) - аналогично. Такие дела. Может кто чего знает? P.S. Кириллица используется по настоянию клиента. Да и раньше особых проблем не было. P.P.S. Тестовый набор в размере 2-х таблиц, двух UDF и сего творения (всего 100kb в архиве) готов сбросить по e-mail любому. Помогите кто может!!! ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 03.05.2001, 08:13 |
|
||
|
То ли сервер глюкавый, то ли руки кривые... HELP!
|
|||
|---|---|---|---|
|
#18+
А deallocate ПереченьРасходов не пробовали делать ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 03.05.2001, 09:43 |
|
||
|
То ли сервер глюкавый, то ли руки кривые... HELP!
|
|||
|---|---|---|---|
|
#18+
Вообще циклы с курсорами пишуться чуть по-другому open ПереченьРасходов fetch next from ПереченьРасходов into @КодДвижения , @КоличествоРасхода , @ФлагПартии WHILE @@FETCH_STATUS = 0 begin insert into @ЖурналРасходов select * from dbo.СписаниеFIFOРасходы(@КодДвижения) fetch next from ПереченьРасходов into @КодДвижения , @КоличествоРасхода , @ФлагПартии end У Вас же получается, что первый раз переменная @@FETCH_STATUS была нуль, затем при выходе из цикла она стала не нулевой и соответственно в цикл больше никогда не войти. Опять же могут быть проблеммы если курсор пустой, а Вы будете думать что считали оттуда одну запись. Насчет deallocate тоже верно, но мне кажется что при выходе из процедуры они(курсоры) сами должны убиться(но не уверен) и это не должно было влиять. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 03.05.2001, 10:43 |
|
||
|
То ли сервер глюкавый, то ли руки кривые... HELP!
|
|||
|---|---|---|---|
|
#18+
После использования курсора надо его явно закрыть и удалить. close cur1 deallocate cur1 Сам он при выходе из процедуры не удалится. Правда, при вторичном проходе по open cur1 (без удаления в предыдущем) вывалилась бы ошибка "курсор cur1 уже есть". А вот если молча возвращает пустой набор записей, то дело, скорее всего, не в этом. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 03.05.2001, 15:58 |
|
||
|
То ли сервер глюкавый, то ли руки кривые... HELP!
|
|||
|---|---|---|---|
|
#18+
Да, GreenSunrise прав, конечно должно быть сообщение об ошибке, не сообразил сразу хотя считаю что все рано лучше явно все прописывать. Да и если в рамках одного и того же коннекта вызывалась процедура, ошибка должна быть однозначно, сам по забывчивости нарывался не раз, я правда работаю в основном на семерке, поэтому в качестве источника функцию не использовал. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 03.05.2001, 16:24 |
|
||
|
То ли сервер глюкавый, то ли руки кривые... HELP!
|
|||
|---|---|---|---|
|
#18+
Во-первых: Большое спасибо всем откликнувшимся. Во-вторых: 2Genady: close ПереченьРасходов deallocate ПереченьРасходов в процедуре само собой были. Это я сократил для читабельности. Видимо напрасно. В случае незакрытия и неубиения курсора сервер аккуратно выдает сообщение об ошибке. Так что проблема не в этом. 2SergSuper: Теоретически с Вами согласен. Практически, если курсор не пустой, все должно работать. Впрочем Ваш вариант работает точно также т.е. - один раз. Так что проблема и не в этом тоже. 2GreenSunrise and ALL: >А вот если молча возвращает пустой набор записей, то дело, скорее всего, не в этом. Дело судя по всему действительно не в этом. Ошибка начала возникать после переустановки сервера и не только в этой процедуре, а во всех процедурах, использующих в теле вызовы UDF . В том числе в тех, которые написаны в точном соответствии с советом SergSuper. А особая мистика в том, что вновь созданная процедура, дословно повторяющая старую работает нормально. Такие дела. Судя по всему дело в каких-то установках сервера. Может у кого есть идеи в каких? А то чего то пересоздавать все SP не очень хочется. Как все-таки получается, что на Open и Debug в QA одна и та же SP отрабатывет нормально, а на exec начинает фокусничать? Сталкивался ли кто-либо с подобными вещами, и как боролся? Еще раз спасибо Всем. А я продолжу пока эксперимент . ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 04.05.2001, 03:39 |
|
||
|
То ли сервер глюкавый, то ли руки кривые... HELP!
|
|||
|---|---|---|---|
|
#18+
А если вместо declare create table #Tmp1 () Insert into #TMP1 Select ... /* или Построчно */ ... Select * from #tmp1 drop table #tmp1 Moth P.S. Если что кидай на мыло /*3 MB*/ moth@mail.primorye.ru ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 04.05.2001, 07:37 |
|
||
|
То ли сервер глюкавый, то ли руки кривые... HELP!
|
|||
|---|---|---|---|
|
#18+
У тебя что, все на русском названия таблиц и функций? был у меня такой кадр, который в 6.5 любил все по русски называть и у него были такие пириблеммы что нужно перекомпилить чтобы заставить работать процедуру... а мой совет не пользуйтеся курсорами лучше перегоняйте во времянку с Identity а потом пошагово в цикли считывайте записи и изменяйте больше кода но зато быстрей и безглючней будет работать я от таких проблемм избавился когда перестал курсоры юзать... ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 04.05.2001, 10:27 |
|
||
|
То ли сервер глюкавый, то ли руки кривые... HELP!
|
|||
|---|---|---|---|
|
#18+
2 Andrew В общем дело ясное, что дело темное Попробуйте просто перекомпилить все такие процедуры, ну в общем с моей стороны советы построены на гадании сам с такой проблемой не сталкивался. 2 hermit Вы полагаете, что если прегонять во временную таблицу и читать потом из нее в цикле быстрее будет? Хм.... Непонятно, непротив услышать объяснение. Сам всегда полагал, что решение использовать временную таблицу стоит того тогда, когда можно при этом избежать цикла ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 04.05.2001, 10:54 |
|
||
|
То ли сервер глюкавый, то ли руки кривые... HELP!
|
|||
|---|---|---|---|
|
#18+
To Genady Да, Быстрее.... Не всегда но в большинстве случаев (покрайней мере не медленее) особенно если в той таблице есть поля которые нужно прообдейтить в зависимости от некоторых факторов. и полей таких до 10 штук Это все проверенно на личном опыте в некоторых местах быстрее в 5-6 раз получалось.. И что самое приятное... намного менее глючней. У меня 2 года крутится база на 6.5 где с полтора десятка модулей.... около 300 сохраненок вообщем автоматизированн полностью завод... и поверь, отчеты довольно сложные есть везде я обходился без курсоров.. и я уже забыл как сервер выглядит пото му что к нему не подходил уже давно все работает .... а ведь были проблеммы которые были у товарисча который написал в самом первом письме убрал курсоры, ушли проблеммы... еще меня правда сумщает названия на русском языке ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 04.05.2001, 11:42 |
|
||
|
То ли сервер глюкавый, то ли руки кривые... HELP!
|
|||
|---|---|---|---|
|
#18+
Присоединяюсь. В процедуре собирал данные во временную таблицу курсором в цикле (7.0), но в итоге селект * из временной таблицы ничего не возврашал, хотя записи там точно были! Метод решения - отказ от курсоров. Хотя иногда удавалось завести процедурку, избавевшимь только от части курсоров (вложенные циклы). В общем никакой системы обнаружить не удалось. Microsoft, однако. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 04.05.2001, 12:26 |
|
||
|
То ли сервер глюкавый, то ли руки кривые... HELP!
|
|||
|---|---|---|---|
|
#18+
To Genady И я присоединяюсь. Быстрей и безглючней. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 04.05.2001, 13:03 |
|
||
|
То ли сервер глюкавый, то ли руки кривые... HELP!
|
|||
|---|---|---|---|
|
#18+
2 Всем присоеденившимся То ли народ не понял мой вопрос, то ли я ничего не понимаю Мне бы хотелось получить обоснование (объяснение) почему цикл на временной таблице быстрее цикла на курсоре? P.S. Как и все нормальные люди, я тоже избегаю использования курсоров, посему о глюках с ними ничего сказать не могу, не встречал. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 04.05.2001, 14:25 |
|
||
|
То ли сервер глюкавый, то ли руки кривые... HELP!
|
|||
|---|---|---|---|
|
#18+
А вот почему быстрей, это я уже не скажу Не знаю видно при курсорах используется внутри еще что-то, что при больших данных замедляет общий процесс.... (память выделяет, чегото запоминает для движения по записям..) в при времянках один TSQL и ничего более ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 04.05.2001, 15:05 |
|
||
|
То ли сервер глюкавый, то ли руки кривые... HELP!
|
|||
|---|---|---|---|
|
#18+
>А вот почему быстрей, это я уже не скажу Не знаю Жаль, тогда остается потестировать если что нибудь интересное обнаружу - сообщу. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 04.05.2001, 15:11 |
|
||
|
То ли сервер глюкавый, то ли руки кривые... HELP!
|
|||
|---|---|---|---|
|
#18+
2 всем присоеденившимся Ребята, вы ничего не путаете? Создал таблицу create table table3 (id int identity(1,1), name varchar(50)) загнал в нее 100000 записей и написал две процедуры со временной таблицей CREATE PROCEDURE test3t AS begin declare @vI int, @stop int create table #test (tempkey int identity(1,1), oldkey int, field varchar(50)) set @stop = @@identity set @vI = 1 insert into #test select * from table3 where id between 20000 and 50000 while @vI <= @stop begin select field from #test where tempkey = @vI set @vI = @vI + 1 end drop table #test end и с курсором CREATE PROCEDURE test3c AS begin declare @tempname varchar(50) declare tempcur cursor for select name from table3 where id between 20000 and 50000 open tempcur fetch next from tempcur into @tempname WHILE @@FETCH_STATUS = 0 BEGIN PRINT @tempname fetch next from tempcur into @tempname END close tempcur deallocate tempcur end Время выполнения test3t - 11 мин 26 сек Время выполнения test3c - 0 мин 22 сек Затем модифицировал test3t добавил первичный ключ во временную таблицу - время выполнения - 0:40 т.е. все равно медленней!!!!!!! ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 04.05.2001, 16:57 |
|
||
|
То ли сервер глюкавый, то ли руки кривые... HELP!
|
|||
|---|---|---|---|
|
#18+
Если ты используешь конструкцию типа CREATE FUNCTION fncTest() RETURNS @tbTable TABLE ( Field int PRIMARY KEY ) AS BEGIN INSERT @tbTable SELECT SrcField FROM tbSrcTable RETURN END То советую попробовать с такой конструкцией CREATE FUNCTION fncTest() RETURNS TABLE RETURN( SELECT SrcField FROM tbSrcTable ) С первой у меня были проблемы с кол-вом возвращаемых записей Удачи ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 04.05.2001, 18:53 |
|
||
|
То ли сервер глюкавый, то ли руки кривые... HELP!
|
|||
|---|---|---|---|
|
#18+
To Genady: Если сделать вложенную процедуру, то результат: TextData CPU Reads Writes Duration exec aaa_test1 2547 87531 0 13436 exec aaa_test2 2875 108085 0 12716 Т.е. разницы нет, но при использовании вр. таблиц иногда можно делать обработку не построчно, меньше глюков и т.д. drop PROCEDURE aaa_test1 drop PROCEDURE aaa_test11 drop PROCEDURE aaa_test2 go CREATE PROCEDURE aaa_test11 WITH RECOMPILE AS declare @vI int declare @tempname varchar(50) set @vI = 1 while 1=1 begin select @tempname = field from #test where tempkey = @vI if @@rowcount = 0 break PRINT @tempname set @vI = @vI + 1 end go CREATE PROCEDURE aaa_test1 AS declare @vI int, @stop int declare @tempname varchar(50) create table #test ( tempkey int identity(1,1) primary key clustered, oldkey int, field varchar(50) ) insert into #test(oldkey, field) select ctID, Code from tblCatalog exec aaa_test11 drop table #test go --и с курсором CREATE PROCEDURE aaa_test2 AS declare @tempname varchar(50) declare tempcur cursor for select Code from tblCatalog open tempcur fetch next from tempcur into @tempname WHILE @@FETCH_STATUS = 0 BEGIN PRINT @tempname fetch next from tempcur into @tempname END close tempcur deallocate tempcur go ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 07.05.2001, 15:37 |
|
||
|
То ли сервер глюкавый, то ли руки кривые... HELP!
|
|||
|---|---|---|---|
|
#18+
2 alexeyvg >но при использовании вр. таблиц иногда можно делать обработку не построчно Так я с этим не спорю, я не поверил, что цикл на временной таблице быстрее курсора, и как видите не зря. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 07.05.2001, 16:14 |
|
||
|
То ли сервер глюкавый, то ли руки кривые... HELP!
|
|||
|---|---|---|---|
|
#18+
Всем большое спасибо. Главное заинтересовать общественность и уехать в командировку . После неоднократных перустановок сервера и перекомпиляции процедур все заработало. Почему заработало определить не удалось. Воспроизвести ошибку на другом сервере не удалось так же. Жаль. Ну да ладно. Подкину еще один интересный момент, имеющий отношение, как к выбору между переменными типа table и временными таблицами, так и к мистике, исполняемой иногда сервером. Итак: CREATE procedure Numbers_p (@n bigint = 100000) as begin declare @m bigint declare @Table table (i bigint , k bigint) set @m=0 while @m<@n begin set @m=@m+1 insert into @Table values (@m , @m) end select * from @Table end или так: CREATE procedure Numbers_vr (@n bigint = 100000) as begin declare @m bigint create table #Table (i bigint , k bigint) set @m=0 while @m<@n begin set @m=@m+1 insert into #Table values (@m , @m) end select * from #Table end Во первых работает быстрее на разных машинах то первый вариант, то второй (от чего зависит так и не понял). Но чаще первый быстрее (в среднем на 20-30%), оно и понятно, если памяти хватает, то таблицы-переменные по идее должны работать быстрее. А вот если оперетивки не хватает, да процессор слабый, да файл подкачки маловат и увеличивается по ходу выполнения процедуры, то запросто можно получить 100 000 записей, последняя из которых будет не 100000, 100000 , а например 99992, 99992. Я неоднократно воспроизводил подобное у клиентов на "серверах" типа Celeron 366, 64 MB, особенно если минимальный размер файла подкачки не увеличить заранее. Можно конечно иронизировать по поводу конфигурации машины. Но во-первых, чего еще нужно на рабочую группу из 5 пользователей? Во-вторых, если серверу не хватает ресурсов, IMHO, он должен об этом сообщить, а не выдавать после 4 минут работы неверный результат. Или может я чего неверно понимаю? Главное не понятно, как бороться с подобными вещами. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 19.05.2001, 22:32 |
|
||
|
|

start [/forum/topic.php?fid=46&fpage=3575&tid=1826740]: |
0ms |
get settings: |
9ms |
get forum list: |
16ms |
check forum access: |
3ms |
check topic access: |
3ms |
track hit: |
26ms |
get topic data: |
10ms |
get forum data: |
3ms |
get page messages: |
54ms |
get tp. blocked users: |
1ms |
| others: | 264ms |
| total: | 389ms |

| 0 / 0 |
