Название: Qt-4.5.2 поиск по образцу в QTreeView (иерархический справочник ) Отправлено: mal от Август 27, 2009, 10:23 Всем привет!
Ситуация следующая: Для работы с иерархическим справочником (~200 тысяч записей) взял за основу пример simpletreemodel. Для сортировки задал вью QSortFilterProxyModel. И для управления выделением строк задал QItemSelectionModel. Исходный список неотсортирован - сортирую A-Z. Заглушил QTreeView::keyboardSearch , так как мне нужен сквозной поиск по образцу. Образец для поиска задается пользователем: и, ив, ива ... и т.д. При вводе каждой новой буквы беру образец, определяю текущую строку в TreeView, и зову match со следующей строки. Код: QModelIndex idx_cur = tree_view->currentIndex(); Образец поиска находится. При последующем поиске с тем же образцом, повторяю действия выше для поиска со следующей строки от текущей. Вроде бы все работает. И по идее при достижении конца списка поиск должен повториться с нулевой строки. Но вот в чем проблема: поиск "зацикливается" внутри первых 3 веток иерархии. Т.е. образец "и" выдает по кругу (предположим) строку "Ира" в ветках иерархий (предположим по годам) 1970, 1971, 1972. Т.е. поиск крутится внутри нескольких корневых веток по циклу, не выходя за них. Хотя "Ира" присутствует также и во всех последующих корневых ветках справочника - годах 1975,1976 и т.д. Причем если задать поиск с hits = -1, то размерность QModelIndexList indexList - будет несколько тысяч, т.е. поиск поднимает все включения "Ир". Но такой вариант мне не приемлем (найти все образцы за раз, а потом уже идти по таблице беря номера строк из готового indexList). Так как быстрее найти 1-е включение, потом перейти на следующую строку, найти следующее включение и т.д. Но сквозного поиска в моей реализации не получается. ??? Может кто-нибудь подскажет в чем я неправ? Название: Re: Qt-4.5.2 поиск по образцу в QTreeView (иерархический справочник ) Отправлено: mal от Август 27, 2009, 23:51 Поковырялся немного. Вижу уже ошибку: при определении следующего индекса для поиска надо проверять есть ли дети у текущей строки.
Если есть, то "проваливаемся" глубже, если нет, то смотрим есть ли парент у текущей записи, проверяем сколько детей у парента, и если их больше, чем номер текущей строки, строим индекс для поиска увеличивая номер текущей строки, и используем парент текущей строки Код: QModelIndex idx_cur = tree_view->currentIndex(); правда пока не понял как выходить выше, если в текущей ветке не найдено больше строк с заданным образцом поиска, т.е. Код: QModelIndexList indexList = proxyModel->match(idx_next , Qt::DisplayRole, var, 1, Qt::MatchStartsWith | Qt::MatchWrap | Qt::MatchRecursive); Название: Re: Qt-4.5.2 поиск по образцу в QTreeView (иерархический справочник ) Отправлено: Авварон от Август 28, 2009, 08:22 idx_next.parent?
Название: Re: Qt-4.5.2 поиск по образцу в QTreeView (иерархический справочник ) Отправлено: mal от Август 28, 2009, 10:57 Авварон
нет это понятно, вопрос скорее алгоритмический: стоим мы на текущей строке, у нее есть дети. образец для поиска не меняется - т.е. по акселератору продолжаем поиск с тем же образцом. Случилось так, что внутри иерархии текущей строки, не нашлось строки совпадающей с образцом поиска. Т.е. indexList.count() == 0. Текущая строка не сменилась. В теории надо сдвинуться дальше по текущему уровню иерархии и повторить поиск. Если текущая строка в иерархии последняя - вернуться на уровень выше ( если есть парент) или, если текущая строка последняя в корневой иерархии - вернуться на начало таблицы и повторить поиск с индексом idx_next = proxyModel->index(0,0) Далее возникает вопрос как не свалиться в бесконечный цикл, если искомой строки в списке нет вовсе. Например мы стоим где то внутри списка и задаем имя начинающееся с твердого знака. Такой строки в таблице нет. ---- Хотя наверно если поиск шел сначала списка и не нашлось искомых совпадений - тут и поиску конец. :) Название: Re: Qt-4.5.2 поиск по образцу в QTreeView (иерархический справочник ) Отправлено: BRE от Август 28, 2009, 11:00 Далее возникает вопрос как не свалиться в бесконечный цикл, если искомой строки в списке нет вовсе. Можно запомнить строку (индекс) с которой начался поиск (по данной маске) и если мы опять пришли к ней, обойдя все дерево, остановиться.Например мы стоим где то внутри списка и задаем имя начинающееся с твердого знака. Такой строки в таблице нет. Название: Re: Qt-4.5.2 поиск по образцу в QTreeView (иерархический справочник ) Отправлено: Авварон от Август 28, 2009, 11:27 что-то тут явно не так:( зачем искать в текущей, если в случае облома мы все равно обходим все дерево?
added: а, то есть результат из текущей ветки приоритетней? тут 2 способа - либо искать в ней, а затем сразу с корня, либо искать с корня все похожие и смотреть чтобы результат был внутри нужной ветки Название: Re: Qt-4.5.2 поиск по образцу в QTreeView (иерархический справочник ) Отправлено: mal от Август 28, 2009, 11:33 "...Хотя наверно если поиск шел сначала списка и не нашлось искомых совпадений - тут и поиску конец. Улыбающийся ..."
это конечно бред Авварон а что ты предлагаешь? у текущей есть дети, у которых в свою очередь детей уже нет (последний уровень иерархии для текущей ветки) и среди этих детей искомого образца не найдено. Надо двигаться дальше насквозь через всю таблицу. Вероятно, надо сделать так, как советует BRE . Авваарон Цитировать added: а, то есть результат из текущей ветки приоритетней? тут 2 способа - либо искать в ней, а затем сразу с корня, либо искать с корня все похожие и смотреть чтобы результат был внутри нужной ветки да конечно - нужно найти ближайшее включение внутри текущей иерархии, и если оно не найдено - перемещаться на другие корни Название: Re: Qt-4.5.2 поиск по образцу в QTreeView (иерархический справочник ) Отправлено: Авварон от Август 28, 2009, 11:41 хм, ближайшее или любое, кроме внутритекущего? возможно что рекурсивное понятие вверх и имеет смысл
Название: Re: Qt-4.5.2 поиск по образцу в QTreeView (иерархический справочник ) Отправлено: mal от Август 28, 2009, 12:00 Авварон
ближайшее от текущего положения вниз, потом, при следующем поиске, ближайшее от найденного и т.д. по кругу :) Название: Re: Qt-4.5.2 поиск по образцу в QTreeView (иерархический справочник ) Отправлено: Авварон от Август 28, 2009, 12:19 не найденного?
Название: Re: Qt-4.5.2 поиск по образцу в QTreeView (иерархический справочник ) Отправлено: mal от Август 28, 2009, 12:26 Авварон
предположим в списке есть 10 идентичных строк в разных уровнях иерархии. В том числе и в разных подуровнях от главного корня. Юзер ввел строку "Ира". Жмет искать. Находим самую первую "Иру" от текущего положения в списке. Найденную строку делаем текущей (скролимся к ней, выделяем ее) Жмет искать еще раз - находим следующую "Иру" ближайшую и т.д. *Ищем от текущего места вглубь иерархии если дети есть, если нет детей - переходим на следущую строку в текущей иерархии и ведем поиск от нее. Если текущая строка последняя в текущей иерархии - поднимаемся на уровень выше, перемещаемся на следущую строку в этом уровне и снова *. Таким образом обходим все дерево. А если во всем дереве не нашлось искомого образца - прерываем поиск как советовал BRE. Вот так я все это вижу. Название: Re: Qt-4.5.2 поиск по образцу в QTreeView (иерархический справочник ) Отправлено: Авварон от Август 28, 2009, 12:29 а я так понял, что мы ищем один раз, и поднимаемся вверх только если в текущей ветке ничего не нашли...
|