Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате |
Форум программистов > Delphi: Базы данных и репортинг > Метод FindKey и TQuery |
Автор: Serggggg 11.2.2004, 14:25 |
Всем привет! Прошу совета. Проблема не очень сущетвенная, но желательно разобраться. Как мы все знаем, у компонента TTable есть такой чудный метод, как FindKey, который после Refresh'а позволяет вернуться к нужной записи. В моем случае используется TQuery. Вышеупомянутого метода для него нет. Запрос "обновляется" посредством операций Active:=False; Active:=True; Курсор (естественно) скачет сразу на первую запись. А как мне перевести его на ту позицию (скажем, Grid'a), с которой перед обновлением запроса производилось, например, удаление записи? |
Автор: x77 11.2.2004, 14:40 |
используя Locate по ключевому полю. в принципе, можно по любому, но Locate использует при поиске индексы, поэтому желательно, чтобы поле было как минимум индексированным, а лучше - ключевым. |
Автор: Kesh 11.2.2004, 15:26 |
Имхо, для квери это не самый лучший способ... Представь, что у тебя клиент, подсоединенный к табличке в базе, в которой записей эдак около миллиона, да еще плюсом есть какое-нить поле типа BLOB/CLOB/BFile. В Oracle при реализации такой квери ты получишь где-то N первых записей, остальные будут подгружаться по мере необходимости. А теперь представь, что ты своим FindKey обращаешься к одной из последних записей в квере... Придется пролистывать всю кверю, плюс тянуть LOB-поля, и все это по сети, а если в BLOB'e еще и картинка, еще и BMP'шная... Представь себе загрузку сети... А если у тебя при этом еще и несколько клиентов... P.S. Все это конечно же ИМХО... |
Автор: Maverick 11.2.2004, 16:21 |
А не лучше перед удалением запомнить номер строки, на которой стоишь... а после обновления - направиться к этому номеру... Разве порядок-нумерация строк изменится? По-моему просто сдвинется на одну запись... Значит, попадешь достаточно близко... Или сам запрос в Query меняется? |
Автор: x77 11.2.2004, 16:22 |
kesh, при описанной тобой ситуации, нужная запись получается отдельным запросом. ну а для всех прочих случаев... есть же, в конце концов, стандартные решения, зачем сразу в крайности? |
Автор: x77 11.2.2004, 16:28 |
Maverick, о том и речь. делаем DisableControls, запись удаляется, курсор сдвигается на строку, запоминается значения ключевого поля (полей), выключается/включается квери, курсор позиционируется на место методом Locate, делаем EnableControls. |
Автор: Maverick 11.2.2004, 16:36 |
Вы меня не поняли.... x77.... Зачем Locate.... Запомнить надо RecNo... Потом вернуться к нему же.... или RecNo+1.... Зачем искать?.... Заранее запомнить... |
Автор: x77 11.2.2004, 16:49 |
Maverick, насколько я знаю, RecNo имеет смысл только для локальных баз (dBase, Paradox, etc.) для Interbase или Oracle RecNo равен -1 или вообще какой-нибудь чепухе. |
Автор: Serggggg 11.2.2004, 18:18 |
Значение ключевого поля - это замечательно. Я и сам сторонник поски по ключу. Но в инспекторе объектов IndexName или IndexFieldName задаётся только для таблиц, а не для запросов. Для компонента TQuery такого свойства там не описано. x77, база действительно на Oracle. |
Автор: Kesh 11.2.2004, 18:47 |
И все же для квери запоминать какой-то номер мне кажется не есть гуд... Ибо для реляционых баз данных, в силу определения, нет понятия первая, предыдущая, последующая, последняя запись... Важно только условие выборки... |
Автор: Maverick 11.2.2004, 18:58 |
x77.... Ты прав.... Пробую под Informix - =-1.... Буду знать.... |
Автор: Петрович 12.2.2004, 10:26 | ||||||
Для реляционных БД понятия "номер строки" - несуществует. Даже в локальных БД (dBase, Paradox, и п.р.) в которых действителен RecNo, такой метод не годится! Поскольку во первых, помимо тебя, в таблице могут копошиться и другие юзеры которые могут вставлять/удалять записи. И во вторых, возможны запросы манипулирующие неопределенным числом записей, например DELETE FROM TABLE Vasya WHERE Price > 100 Правильным способом будет использовать Locate. Если есть primary key, то использовать его, если нет, то можно использовать все поля. Например можно описать такой объект:
А потом его использховать, например так:
|
Автор: Serggggg 12.2.2004, 10:52 |
Благодарю за совет. Стоит попробовать! |
Автор: Maverick 12.2.2004, 17:14 |
[QUOTE]Для реляционных БД понятия "номер строки" - несуществует. Даже в локальных БД (dBase, Paradox, и п.р.) в которых действителен RecNo, такой метод не годится! Поскольку во первых, помимо тебя, в таблице могут копошиться и другие юзеры которые могут вставлять/удалять записи. И во вторых, возможны запросы манипулирующие неопределенным числом записей, например DELETE FROM TABLE Vasya WHERE Price > 100[/QUOT] Последнее время были задания для DBF для работы одного пользователя.... в стиле с навигатором ДОБАВИТЬ/УДАЛИТЬ.... Вот и дошел до ручки.... |
Автор: cvi 13.2.2004, 19:05 |
Вижу моего решения еще нет. Пишу так var Save_Place : TBookMark; Save_Place := Query.(Что то типа)SaveBookMark;(точно не помню как называется) Query.Actice := False; Query.Active := True; Query.GotoBookMark(Save_Place); Query.FreeBookMark(Save_Place); точно работает по Interbase, paradox Спасибо за внимание. ![]() |
Автор: Medved 13.2.2004, 20:44 | ||
Этот метод называется GetBookmark. Но учтите, вот из F1: GetBookmark relies on a protected method to obtain the bookmark value. TDataSet descendants implement this method to provide their own type of bookmark support. Unidirectional datasets do not support bookmarks, and so do not return a meaningful value. Иначе говоря, GetBookmark не будет работать на однонаправленных наборах данных (т.е. не подлежащих редактированию, кэшированию, фильтрации и индексированию, а также навигации. Такой набор данных напрмер возвращает dbExpress). |
Автор: Петрович 13.2.2004, 21:17 | ||||
Тогда-уж проще:
Однако не стал рекомендовать, поскольку где-то читал что закладка (Bookmark) сохраненная до закрытия датасета может стать недействительной после его открытия. Причем сам когда-то "обжегся" (Interbase через IBX), теперь использую закладки только когда в промежутке не надо закрывать датасет. |
Автор: Medved 13.2.2004, 21:30 | ||
Полностью согласен, пользоваться закладками надо с осторожностью. |