|
Программирование >> Программирование баз данных
NEXT. Перейти к следующей строке. PRIOR. Перейти к предыдущей строке. FIRST. Перейти к первой строке. LAST. Перейти к последней строке. Более подробные сведения о конструкции FETCH приведены ниже в данной главе, а в настоящий момент достаточно отметить, что такая конструкция существует и позволяет управлять перемещением через набор данных курсора. Рассмотрим краткий пример, позволяющий ознакомиться с основными понятиями прокручиваемого курсора. При этом фактически будет использоваться немного измененный вариант хранимой процедуры, созданной в одном из предыдущих разделов настоящей главы: USE AdventureWorks GO CREATE PROCEDURE spCursorScroll AS DECLARE ©Counter int, ©OrderlD int, ©CustomerlD int DECLARE CursorTest CURSOR LOCAL SCROLL SELECT SalesOrderlD, CustomerlD FROM Sales.SalesOrderHeader SELECT ©Counter = 1 OPEN CursorTest FETCH NEXT FROM CursorTest INTO ©OrderlD, ©CustomerlD PRINT Row + CAST(©Counter AS varchar) + has a SalesOrderlD of + CAST (©OrderlD AS varchar) + and a CustomerlD of + CAST (©CustomerlD AS varchar) WHILE (©Counter<=5) AND (©©FETCH STATUS=0) BEGIN SELECT ©Counter = ©Counter + 1 FETCH NEXT FROM CursorTest INTO ©OrderlD, ©CustomerlD PRIOT Row + CAST(©Counter AS varchar) + has a SalesOrderlD of + CAST (©OrderlD AS varchar) + and a CustomerlD of + CAST (©CustomerlD AS varchar) WHILE (©Counter > 1) AND (©©FETCH STATUS = 0) BEGIN SELECT ©Counter = ©Counter - 1 FETCH PRIOR FROM CursorTest INTO ©OrderlD, ©CustomerlD PRINT Row + CONVERT(varchar,©Counter) + has an SalesOrderlD of + CAST (©OrderlD AS varchar) + and a CustomerlD of + CAST (©CustomerlD AS varchar) CLOSE CursorTest DEALLOCATE CursorTest Основные различия по сравнению с предьщущим вариантом состоят в следующем. Курсор объявлен с опцией SCROLL. Вместо ключевого слова NEXT, применявшегося для перемещения, введено новое ключевое слово PRIOR. Доработана применявшаяся ранее хранимая процедура, касающаяся того, что закрытие и освобождение курсора осуществляется непосредственно в самой процедуре, а внешняя процедура для этой цели не используется (иными словами, все действия, выполняемые по отношению к курсору, ограничиваются только одной процедурой). Но наибольший интерес представляют полученные результаты. В данном случае не требуется применять какой-то замысловатый тестовый сценарий; достаточно вызвать процедуру на вьшолнение: EXEC spCursorScroll Полученные результаты показывают, как происходит прокрутка по заказам с разными номерами вперед и назад: Row 1 has а SalesOrderlD of 43659 and a CustomerlD of 676 Row 2 has a SalesOrderlD of 43660 and a CustomerlD of 117 Row 3 has a SalesOrderlD of 43661 and a CustomerlD of 442 Row 4 has a SalesOrderlD of 43662 and a CustomerlD of 227 Row 5 has a SalesOrderlD of 43663 and a CustomerlD of 510 Row 6 has a SalesOrderlD of 43664 and a CustomerlD of 397 Row 5 has an SalesOrderlD of 43663 and a CustomerlD of 510 Row 4 has an SalesOrderlD of 43662 and a CustomerlD of 227 Row 3 has an SalesOrderlD of 43661 and a CustomerlD of 442 Row 2 has an SalesOrderlD of 43660 and a CustomerlD of 117 Row 1 has an SalesOrderlD of 43659 and a CustomerlD of 676 Вполне очевидно, что мы получили возможность успешно перемещаться не только в прямом направлении, как перед этим, но и в обратном. Но когда дело касается сравнения производительности однонаправленного и прокручиваемого курсоров, то обнаруживается, что первый является бесспорно более эффективным по сравнению с вторым. Чтобы понять, в чем состоят причины такого различия, достаточно вспомнить, что при использовании однонаправленного курсора, предназначенного только для чтения, в СУБД SQL Server необходимо следить лишь за тем, каковой является следующая строка, поэтому курсор действует по такому же принципу, как связный список. А в той ситуации, когда приходится изменить позицию в курсоре другими способами, возникает необходимость хранить дополнительную информацию, без которой невозможно обеспечить продуктивный поиск запрашиваемой строки. Как именно решается эта задача, зависит от конкретных выбранных опций курсора. В курсорах некоторых типов возможность прокрутки заложена изначально, а в других курсорах переход в любом направлении не допускается. Курсоры некоторых типов чувствительны к изменениям в данных, внесенным другими процессами, а другие курсоры работают с данными так, как если бы они остались неизменными со времени первоначального получения. Некоторые связанные с этим проблемы рассмотрены в следующем разделе. Типы курсоров Изучение различных API-интерфейсов, предназначенных для работы с курсорами, показывает, что курсоры, вообще говоря, подразделяются на четыре типа: статические; ключевые; динамические; последовательные. Точные способы реализации этих четырех типов (а также их названия) немного изменяются в зависимости от применяемых API-интерфейсов и объектных моделей, но, вообще говоря, в основном остаются одинаковыми. Основными признаками, по которым курсоры различных типов отличаются друг от друга, являются способность к прокрутке и чувствительность к изменениям, вносимым в базу данных на протяжении срока существования курсора. Выше было приведено общее определение понятия прокручиваемости, а что касается термина чувствительность, то его чаще можно встретить в книгах по радиотехнике, а не по программированию. Тем не менее понятие чувствительности становится очень важным, когда речь идет о выборе типа курсора. Является ли курсор чувствительным к сторонним изменениям или нет, зависит от того, позволяет ли он обнаруживать изменения в базе данных, внесенные сторонними процессами, на протяжении срока своего существования. Из определения ч)ъст-вительности следует также, что курсор должен дать возможность выполнять определенные действия после обнаружения такого изменения. Рассмотрим, как реализуется понятие чувствительности курсора на примере двух противоположных типов курсоров - статических и динамических. Статический курсор после его создания полностью игнорирует любые изменения в базе данных, не обусловленные действиями самого курсора. С другой стороны, динамический курсор обнаруживает любые изменения в базе данных (возникшие в связи со вставкой строк, удалением, обновлением и в результате любых других операций модификации данных) до тех пор, пока остается открытым. В этой главе вопросы чувствительности курсора будут рассматриваться при изучении каждого отдельного типа курсора. Статические курсоры Статический курсор можно сравнить с фотоснимком, на котором время застыло. И действительно, по меньшей мере в одной из объектных моделей доступа к данным этот объект именуется не статическим курсором, а набором записей снимка. При создании статического курсора формируется весь относящийся к нему набор записей, который можно сравнить с временной таблицей в базе данных tempdb. А со времени его создания в статическом курсоре ничего не изменяется. Иными словами, такой курсор существует как отдельно взятый объект. Как было указано выше, для работы с курсорами предусмотрено несколько различных объектных моделей, причем одни из них позволяют обновлять информацию в статическом к)соре, а другие - нет, но общий принцип всегда остается одним и тем же: статический курсор не позволяет записывать обновления в базу данных. Прежде чем приступить к более подробному изучению курсора этого типа, необходимо забежать немного вперед и отметить, что ситуации, в которых имеет смысл использовать статический курсор в серверном приложении, встречаются чрезвычайно редко. Тем самым автор не собирается утверждать, что такие ситуации вообще не возникают; это было бы неправильно, но они действительно обнаруживаются исключительно редко. Перед тем как мы перейдем к рассмотрению возможности использования статического курсора в серверном приложении, необходимо ответить на следующие вопросы.
|
© 2006 - 2024 pmbk.ru. Генерация страницы: 0.001
При копировании материалов приветствуются ссылки. |