Форум: "Базы";
Текущий архив: 2008.06.22;
Скачать: [xml.tar.bz2];
ВнизНадо оптимизировать хранимку, как подступиться незнаю&#133 Найти похожие ветки
← →
Kolan © (2008-01-18 10:20) [0]Здравствуйте,
Есть хранимка не сложная для понимания. Состоит из одного фетча. Её работу надо оптимизировать по скорости. Дали задание переписать её с помощью запроса.
Назнаю с чего начать, что-бы прочесть такого для, того, чтобы задание выполнить?
ЗЫ
Хранимка такая:
Комменты мои.CREATE PROCEDURE dbo.proc_poli_findpac6(@userid int) AS
/*@userid — код пользователя, который работает с системой.*/
update tmp_talon
set kodp_orig = kodp
where uid = @userid
update tmp_pacient
set kodp_orig = kodp
where uid = @userid
/*Объявить курсор …*/
declare sp_cursor_find_pac cursor for
select nreestr, kodlpu, nsvod, kodp, famip, namep, otchp, polpa, drogd, adres, kterr,
kodst, nstra, ndela, seria, npoli, viddk, serdk, nomdk, prrab, rabot, cnils, innst, kppst, regn_oms, uid
from TMP_PACIENT
where UID = @userid
declare @nreestr float
declare @kodlpu float
declare @nsvod smallint
declare @kodp numeric(18,0)
declare @famip varchar(25)
declare @namep varchar(20)
declare @otchp varchar(20)
declare @polpa varchar(1)
declare @drogd datetime
declare @adres varchar(110)
declare @kterr smallint
declare @kodst smallint
declare @nstra varchar(50)
declare @ndela varchar(10)
declare @seria varchar(15)
declare @npoli varchar(10)
declare @viddk smallint
declare @serdk varchar(10)
declare @nomdk varchar(10)
declare @prrab smallint
declare @rabot varchar(60)
declare @cnils varchar(20)
declare @innst varchar(14)
declare @kppst varchar(9)
declare @regn_oms varchar(15)
declare @uid int
declare @cnt int
declare @ident int
open sp_cursor_find_pac
/*Выбрать данные из курсора*/
fetch next from sp_cursor_find_pac into
@nreestr, @kodlpu, @nsvod, @kodp, @famip, @namep, @otchp, @polpa, @drogd, @adres, @kterr,
@kodst, @nstra, @ndela, @seria, @npoli, @viddk, @serdk, @nomdk, @prrab, @rabot, @cnils, @innst, @kppst,@regn_oms,@uid
while (@@FETCH_STATUS = 0)
begin
/*Получить количество пациентов, таких-же как текущий из вр. таблицы.*/
set @cnt =
(
select count(*)
from vpacient
where (@famip is not null and famip = @famip)
and (namep = @namep) and (otchp = @otchp) and (drogd = @drogd) and (npoli = @npoli)
and (cnils = @cnils) and (adres = @adres) and (kodst = @kodst) and (nstra = @nstra)
and (serdk = @serdk) and (nomdk = @nomdk) and (kterr = @kterr) and (ndela = @ndela)
and (innst = @innst) and (kppst = @kppst) and (regn_oms = @regn_oms) and (prrab = @prrab)
)
/*Если таких пациентов нет, то…*/
if (@cnt = 0)
begin
/*…добавить пациента в таблицу.*/
insert into vpacient(famip, namep, otchp, polpa, drogd, adres, kterr,
kodst, nstra, ndela, seria, npoli, viddk, serdk, nomdk, prrab, rabot, cnils, innst, kppst, regn_oms)
values (@famip, @namep, @otchp, @polpa, @drogd, @adres, @kterr,
@kodst, @nstra, @ndela, @seria, @npoli, @viddk, @serdk, @nomdk, @prrab, @rabot, @cnils, @innst, @kppst, @regn_oms);
/*Получить значение только что вставленной строки.*/
set @ident = (select @@IDENTITY)
update tmp_talon
set kodp = @ident
where (uid = @userid)
and (kodlpu = @kodlpu) and (kodp_orig = @kodp) and (nreestr = @nreestr) and (nsvod = @nsvod)
update tmp_rod
set kpaci = @ident
where (uid = @userid)
and (kodlpu = @kodlpu) and (kodp = @kodp) and (nreestr = @nreestr) and (nsvod = @nsvod)
end
else
begin
/*Иначе…*/
/*Получить код первого пациента из найденных.*/
set @ident =
(
select top 1 kpaci
from vpacient
where (famip = @famip)
and (namep = @namep) and (otchp = @otchp) and (drogd = @drogd) and (npoli = @npoli)
and (cnils = @cnils) and (adres = @adres) and (kodst = @kodst) and (nstra = @nstra)
and (serdk = @serdk) and (nomdk = @nomdk) and (kterr = @kterr) and (ndela = @ndela)
and (innst = @innst) and (kppst = @kppst) and (regn_oms = @regn_oms) and (prrab = @prrab)
)
update tmp_talon
set kodp = @ident
where (uid = @userid)
and (kodlpu=@kodlpu) and (kodp_orig = @kodp) and (nreestr = @nreestr) and (nsvod = @nsvod)
update tmp_rod
set kpaci = @ident
where (uid = @userid)
and (kodlpu = @kodlpu) and (kodp = @kodp) and (nreestr = @nreestr) and (nsvod = @nsvod)
end
/*Выбрать следующую строку*/
fetch next from sp_cursor_find_pac into
@nreestr, @kodlpu, @nsvod, @kodp, @famip, @namep, @otchp, @polpa, @drogd, @adres, @kterr,
@kodst, @nstra, @ndela, @seria, @npoli, @viddk, @serdk, @nomdk, @prrab, @rabot, @cnils, @innst, @kppst, @regn_oms, @uid
end;
/*Закрыть и освободить курсор.*/
close sp_cursor_find_pac
deallocate sp_cursor_find_pac
GO
← →
MsGuns © (2008-01-18 10:35) [1]Ключи от квартиры ?
← →
Kolan © (2008-01-18 10:36) [2]> Ключи от квартиры ?
Где деньги лежат?
← →
clickmaker © (2008-01-18 15:22) [3]зачем дважды выполнять селект на предмет существования?
можно сразу попытаться получить id, если его нет, то добавлять
для повышения скорости можно еще
declare sp_cursor_find_pac cursor fast_forward for
← →
Павел Калугин © (2008-01-18 16:58) [4]> (
> select top 1 kpaci
> from vpacient
> where (famip = @famip)
> and (namep = @namep) and (otchp = @otchp) and (drogd
> = @drogd) and (npoli = @npoli)
> and (cnils = @cnils) and (adres = @adres) and (kodst
> = @kodst) and (nstra = @nstra)
> and (serdk = @serdk) and (nomdk = @nomdk) and (kterr
> = @kterr) and (ndela = @ndela)
> and (innst = @innst) and (kppst = @kppst) and (regn_oms
> = @regn_oms) and (prrab = @prrab)
> )
а ордер бай где?
и вообще описал бы задачу что откуда достать надо слоавми а?
← →
Kolan © (2008-01-18 17:08) [5]> declare sp_cursor_find_pac cursor fast_forward for
В справке нет…
Пользую MS SQL Server 2000.
> и вообще описал бы задачу что откуда достать надо слоавми
> а?
Смысл, на сколько я сам понял. Есть dbf из них данны загружаются в таблицыTemp_…
Надо теперь из этих tmp_перенести в основные таблицы.
В таблице пациенты.
По этому условию:(famip = @famip)
and (namep = @namep) and (otchp = @otchp) and (drogd = @drogd) and (npoli = @npoli)
and (cnils = @cnils) and (adres = @adres) and (kodst = @kodst) and (nstra = @nstra)
and (serdk = @serdk) and (nomdk = @nomdk) and (kterr = @kterr) and (ndela = @ndela)
and (innst = @innst) and (kppst = @kppst) and (regn_oms = @regn_oms) and (prrab = @prrab)
Сравнивают пациентов. Если совпадает, то одинаковые пациенты.
Переписал так:CREATE PROCEDURE dbo.proc_poli_findpac6(@userid int) AS
update tmp_talon
set kodp_orig = kodp
where uid = @userid
update tmp_pacient
set kodp_orig = kodp
where uid = @userid
/*Вставить пациентов, которых нет в базе*/
insert into vpacient(famip, namep, otchp, polpa, drogd, adres, kterr,
kodst, nstra, ndela, seria, npoli, viddk, serdk, nomdk, prrab, rabot, cnils, innst, kppst, regn_oms)
select famip, namep, otchp, polpa, drogd, adres, kterr,
kodst, nstra, ndela, seria, npoli, viddk, serdk, nomdk, prrab, rabot, cnils, innst, kppst, regn_oms
from TMP_PACIENT
where (UID = @userid)
AND 0 = (select Count(*)
from vpacient
where (vpacient.famip is not null and TMP_PACIENT.famip = vpacient.famip)
and (TMP_PACIENT.namep = vpacient.namep) and (TMP_PACIENT.otchp = vpacient.otchp) and (TMP_PACIENT.drogd = vpacient.drogd) and (TMP_PACIENT.npoli = vpacient.npoli)
and (TMP_PACIENT.cnils = vpacient.cnils) and (TMP_PACIENT.adres = vpacient.adres) and (TMP_PACIENT.kodst = vpacient.kodst) and (TMP_PACIENT.nstra = vpacient.nstra)
and (TMP_PACIENT.serdk = vpacient.serdk) and (TMP_PACIENT.nomdk = vpacient.nomdk) and (TMP_PACIENT.kterr = vpacient.kterr) and (TMP_PACIENT.ndela = vpacient.ndela)
and (TMP_PACIENT.innst = vpacient.innst) and (TMP_PACIENT.kppst = vpacient.kppst) and (TMP_PACIENT.regn_oms = vpacient.regn_oms) and (TMP_PACIENT.prrab = vpacient.prrab))
/*Ключи в tmp_talon попадают из *.dbf фалов. Поэтому их надо обновить на те что в рабочей базе*/
update tmp_talon
set tmp_talon.kodp = A.kpaci
FROM
(
select vpacient.kpaci, TMP_PACIENT.UID, TMP_PACIENT.kodlpu, TMP_PACIENT.kodp, TMP_PACIENT.nreestr, TMP_PACIENT.nsvod
from vpacient, TMP_PACIENT
where (TMP_PACIENT.UID = @userid)
AND (vpacient.famip = TMP_PACIENT.famip)
and (vpacient.namep = TMP_PACIENT.namep) and (vpacient.otchp = TMP_PACIENT.otchp) and (vpacient.drogd = TMP_PACIENT.drogd) and (vpacient.npoli = TMP_PACIENT.npoli)
and (vpacient.cnils = TMP_PACIENT.cnils) and (vpacient.adres = TMP_PACIENT.adres) and (vpacient.kodst = TMP_PACIENT.kodst) and (vpacient.nstra = TMP_PACIENT.nstra)
and (vpacient.serdk = TMP_PACIENT.serdk) and (vpacient.nomdk = TMP_PACIENT.nomdk) and (vpacient.kterr = TMP_PACIENT.kterr) and (vpacient.ndela = TMP_PACIENT.ndela)
and (vpacient.innst = TMP_PACIENT.innst) and (vpacient.kppst = TMP_PACIENT.kppst) and (vpacient.regn_oms = TMP_PACIENT.regn_oms) and (vpacient.prrab = TMP_PACIENT.prrab)
) AS [A]
where (tmp_talon.uid = A.UID)
and (tmp_talon.kodlpu = A.kodlpu) and (tmp_talon.kodp_orig = A.kodp) and (tmp_talon.nreestr = A.nreestr) and (tmp_talon.nsvod = A.nsvod)
update tmp_rod
set tmp_rod.kpaci = A.kpaci
FROM
(
select vpacient.kpaci, TMP_PACIENT.UID, TMP_PACIENT.kodlpu, TMP_PACIENT.kodp, TMP_PACIENT.nreestr, TMP_PACIENT.nsvod
from vpacient, TMP_PACIENT
where (TMP_PACIENT.UID = @userid)
AND (vpacient.famip = TMP_PACIENT.famip)
and (vpacient.namep = TMP_PACIENT.namep) and (vpacient.otchp = TMP_PACIENT.otchp) and (vpacient.drogd = TMP_PACIENT.drogd) and (vpacient.npoli = TMP_PACIENT.npoli)
and (vpacient.cnils = TMP_PACIENT.cnils) and (vpacient.adres = TMP_PACIENT.adres) and (vpacient.kodst = TMP_PACIENT.kodst) and (vpacient.nstra = TMP_PACIENT.nstra)
and (vpacient.serdk = TMP_PACIENT.serdk) and (vpacient.nomdk = TMP_PACIENT.nomdk) and (vpacient.kterr = TMP_PACIENT.kterr) and (vpacient.ndela = TMP_PACIENT.ndela)
and (vpacient.innst = TMP_PACIENT.innst) and (vpacient.kppst = TMP_PACIENT.kppst) and (vpacient.regn_oms = TMP_PACIENT.regn_oms) and (vpacient.prrab = TMP_PACIENT.prrab)
) AS [A]
where (tmp_rod.uid = A.UID)
and (tmp_rod.kodlpu = A.kodlpu) and (tmp_rod.kodp = A.kodp) and (tmp_rod.nreestr = A.nreestr) and (tmp_rod.nsvod = A.nsvod)
GO
ХЗ, правильно или нет … :(
← →
Павел Калугин © (2008-01-18 17:26) [6]ну тогда вижу 2 шага.
1. сформировать правильные ключи
2. сделать insert select
← →
clickmaker © (2008-01-18 17:32) [7]
> [5] Kolan © (18.01.08 17:08)
> > declare sp_cursor_find_pac cursor fast_forward for
>
> В справке нет…
а это что?DECLARE CURSOR
Defines the attributes of a Transact-SQL server cursor, such as its scrolling behavior and the query used to build the result set on which the cursor operates. DECLARE CURSOR accepts both a syntax based on the SQL-92 standard and a syntax using a set of Transact-SQL extensions.
SQL-92 Syntax
DECLARE cursor_name [ INSENSITIVE ] [ SCROLL ] CURSOR
FOR select_statement
[ FOR { READ ONLY | UPDATE [ OF column_name [ ,...n ] ] } ]
Transact-SQL Extended Syntax
DECLARE cursor_name CURSOR
[ LOCAL | GLOBAL ]
[ FORWARD_ONLY | SCROLL ]
[ STATIC | KEYSET | DYNAMIC | FAST_FORWARD ]
[ READ_ONLY | SCROLL_LOCKS | OPTIMISTIC ]
[ TYPE_WARNING ]
FOR select_statement
[ FOR UPDATE [ OF column_name [ ,...n ] ] ]
...
FAST_FORWARD
Specifies a FORWARD_ONLY, READ_ONLY cursor with performance optimizations enabled. FAST_FORWARD cannot be specified if SCROLL or FOR_UPDATE is also specified. FAST_FORWARD and FORWARD_ONLY are mutually exclusive; if one is specified the other cannot be specified.
← →
Kolan © (2008-01-18 17:51) [8]> FAST_FORWARD
Ааа, теже уши, незначитально изменилось.
А вот запрос гораздо быстрее(в сто раз почти), лиш бы пральный был…
Страницы: 1 вся ветка
Форум: "Базы";
Текущий архив: 2008.06.22;
Скачать: [xml.tar.bz2];
Память: 0.49 MB
Время: 0.045 c