2014-01-07 2 views
0

У меня возникла проблема с clientdataset и методом findnearest.Delphi 2009 - clientdataset findnearest

Я показываю ряд записей в dbgrid и используя заголовок, нажмите, чтобы изменить индекс и сортировать сетку. Я также могу дважды щелкнуть по столбцу, чтобы изменить столбец от возрастающей до сортировки по убыванию. Кроме того, после того, как я нажимаю на столбец, у меня есть поле Tedit, в котором пользователь может ввести данные, а программа использует метод findnearest, чтобы найти ближайшее совпадение в столбце, который был нажат. Он делает это для восходящих или нисходящих индексов.

Моя проблема в том, что когда индекс находится в нисходящей последовательности, findnearest выбирает запись после той, которая должна быть выбрана.

Вот некоторые данные, один набор данных по возрастанию, другой по убыванию.

по возрастанию - Способный, Арнольд, Арни, Barney, Bubba

по убыванию - Bubba, Barney, Арни, Арнольд, Способный

Когда я искать "А" по возрастанию, как указатель земли на Способный. Когда я ищу «B» по убыванию, указатель записи приземляется на Arney. Мои два примера - это не теория, это то, что на самом деле происходит.

Мои вопросы - в порядке убывания, почему он пропускает Bubba и Barney? Пожалуйста, не давайте мне другого примера. Пожалуйста, используйте мои данные, если вы собираетесь привести пример. Пожалуйста, дайте мне объяснение, почему findnearst пропускает первые две записи в нисходящей последовательности, которые явно начинаются с буквы «B».

+0

Ответ не изменится, независимо от того, сколько раз вы меняете данные образца. То же самое, если вы используете 'A, B, C' или' D, E, F' или 'W, Y, Z' или' Fred, Barney и Wilma'. Это та же проблема, и тот же ответ, независимо от того, сколько способов вы его просите.Я объяснил это, используя ваши данные, и вместо того, чтобы читать то, что я написал (несколько раз), вы просто изменили данные, чтобы задать вопрос. –

+1

@Owen - Это очень просто: в порядке убывания «B» «больше, чем« Bubba »и« Barney ». Вот почему «B» пропускает «Bubba». –

+0

Спасибо Sertac, но не B меньше, чем Bubba? Почему, когда я смотрю «Бу», он приземляется на Арни? – Owen

ответ

3

Я могу объяснить, почему это так (надеюсь, с некоторой ясностью) и почему это на самом деле правильное поведение. (В следующем описании будет просто обсуждать однобайтовые символы для простоты, но ответ должен применяться и к другим.)

Учитывая следующие данные (я намеренно сделал их несколько разными для более легкого объяснения - вы увидите почему ниже, надеюсь), давайте предположим, что мы находимся в верхнем ряду (A для восходящего и Charlie для нисходящего) в обоих случаях.

(Ascending)   (Descending) 
LastName   LastName 
========   ======== 
A     Charlie 
Abe     Bob 
Ada     Ada 
B     Abe 
Bob     A 

Начиная с первой строки (строка ) в порядке возрастания и поиск Ac, мы сталкиваемся с Abe первым. Это не совпадение, и то, что мы ищем, должно быть после него в порядке возрастания, поэтому мы продолжаем искать Ac.

Это не так, и теперь мы находимся в той строке, где будет найден матч, который является строкой сразу после этого (Ada). Другими словами, мы находимся в месте, где было бы матч, если бы он присутствовал (ближайший ряд).

Теперь предположим, что мы ищем Al. Мы находимся в Ada, поэтому переходим к следующему ряду и находим, что нет Al.Мы находимся сейчас в B, где Al был бы найден, если бы он был. Другими словами, мы находимся в ближайшем номере . (Это можно подтвердить с помощью быстрого теста.)

Когда мы находимся в порядке убывания, примеры работают одинаково. (Помните, я сделал данные немного отличаются, чтобы сделать его проще объяснить.) Давайте искать Cecil:

Мы в первом ряду, Чарли и перейти к следующей строке поиска для Ce (который был бы послеCharlie в порядке убывания, а не до того, как показано Abe и A в данных выше). Мы обнаруживаем, что у нас нет матча, и в настоящий момент мы находимся в строке Bob, где C был бы найден, если бы он был найден. Другими словами, в порядке убывания мы находимся в ближайшей строке, как и в восходящем примере.

Таким образом, нет проблем в FindNearest. Если вы хотите, чтобы поведение было другим, вы должны реализовать его в своем коде (проверьте, не найдено ли вы точное совпадение, и если не нужно перенести одну строку ранее, если это необходимо, и проверьте, находится ли она там, где вы хотите вместо этого).

+0

Благодарим вас за объяснение, и это имеет смысл. Но по нисходящим данным мы могли бы: – Owen

+0

Спасибо за объяснение, и это имеет смысл. Но по нисходящим данным у нас могут быть: Чарли, Кирли, Чоси, Клем, Боб, Ада, Абэ А. И когда я ищу C, он укажет на Боба. Так что кажется, что он пропускает все, что у него есть. – Owen

+0

Это правильно. Он не пропускает все C. См. Мой ответ, последние три абзаца. Это точно объясняет, что происходит, когда вы ищете только «C». «C» появляется после «Charlie», поэтому он найдет «Charlie», перейдем к следующей строке, ищем «C» в одиночку, и не найдем его. Поэтому мы находимся на * ближайшей строке *, как я уже объяснял выше. ** точное поведение ** и причины для них находятся в моем ответе, и решение обходить это поведение находится в последнем абзаце этого ответа. Поведение правильное в соответствии с правилами сортировки символов (сортировка). –

1

Хорошо, я поеду.

Ваша основная проблема заключается в том, что вы думаете, что FindNearest должен «знать», в каком порядке находятся элементы. т. Е. Поведение, которое вы хотите, - это когда список находится в порядке убывания, который вы хотите, чтобы FindNearest начинал со дна списка и работал вверх.

Это не так, оно всегда работает сверху, вы можете доказать это довольно легко, указав его неупорядоченный список.

+1

Удачи. Я уже сказал это: «Начиная с ** первой строки ** (строка А)» в порядке возрастания и «Мы в ** первом ряду **, Чарли, и переходим к следующей строке, ища Се», , Надеюсь, тебе повезло больше, чем я. :-) В удаленном «ответе», который он опубликовал, он даже указывает, что он понимает поведение в порядке возрастания («если я наберу« ac », он приземлится на baa. Это работает так, как должно».), Но думает, * точное то же поведение ** в порядке убывания неверно. Я объяснил это по крайней мере шесть раз (три выше и еще три в комментариях, оставшихся на «ответ», который ушел, все безрезультатно. –

+0

Думал, что помогу вам, когда я увижу, что его собственный ответ отмечен как не ответ, а это не так. –

+0

Я провел два дня, повторяя одно и то же по-разному, пытаясь пройти, безрезультатно. Я рисовал, использовал меньшие слова, использовал разные данные, чтобы попытаться сделать это яснее ... Все, что у меня есть, - это головная боль. Нет, спасибо, нет у него (от него), нада. Ну, я думаю, что я получил «со всем уважением» перед тем, как оскорблять мой интеллект. :-) –

0

В delphi findnearest method выполняет GotoNearest и GotoNearest в соответствии с документацией delphi; позиционирует курсор на записи, которая является либо точной записью, указанной текущими значениями ключа в буфере клавиш, , либо в первой записи, значения которой превышают указанные.

Это имеет смысл в порядке возрастания, у меня есть две записи AU и BU и поиск B. B больше AU, но меньше BU, поэтому он помещает курсор в первую запись, чьи значения превышают указанные - BU.

Но при спуске он работает по-разному с точки зрения результата. Если у меня есть две записи BU и AU в нисходящей последовательности, и я ищу B, курсор приземляется на AU. Это меня смущает. BU больше, чем B, так почему бы не приземлиться на BU?

Причина; В документе указывается, что если нет совпадения, курсор будет помещен в первую запись, значение которой будет отменено. Но на самом деле то, что gotonearest делает, это выполнить getnext. Таким образом, в восходящем индексе getnext является более крупным ключом, но в нисходящем индексе getnext является меньшим ключом.

+0

Ваш третий абзац неточен. Вы говорите, что у вас есть две записи «BU» и «AU» в последовательности. Поэтому у вас нет проблем с принятием факта, что «AU» приходит после (больше) «BU». Но вы, похоже, не можете принять тот факт, что «B» всегда находится между «AU» и «BU». Если у вас есть дополнительная запись «B», ваша последовательность будет «BU», «B», «AU» (вставьте запись и убедитесь сами). Это означает, что * «BU» больше, чем «B» *, является неправильным, что также делает недействительным * «при потере его работы по-разному» *. –

+0

Не работает по-другому, он работает точно так же. Findnearest ничего не знает о упорядоченности предметов. Какой смысл мы все пытаемся сделать, и у вас, похоже, есть настоящая проблема. Попробуйте его с неупорядоченным списком! –

+0

Sertac, я принимаю, что B находится между AU и BU. Восходящая последовательность AU B BU. По убыванию последовательности BU B AU. Когда я говорю, что работает по-другому, я имею в виду результат не внутренних. Да, внутреннее одно и то же, но результат, поиск B в нисходящей последовательности по сравнению с возрастанием приведет к другому результату. Таким образом, в восходящем индексе getnext является более крупным ключом, но в нисходящем индексе getnext является меньшим ключом. Результат другой, да, он работает с getnext одинаково. – Owen

Смежные вопросы