Главная страница
    Top.Mail.Ru    Яндекс.Метрика
Форум: "Основная";
Текущий архив: 2004.08.29;
Скачать: [xml.tar.bz2];

Вниз

Сравнение двух TStringList-ов   Найти похожие ветки 

 
Pavelkq   (2004-08-10 15:27) [0]

Здравствуйте!
Имею два TStringList-а. Один маленький (тысячи записей), другой - огромный (сотни тысяч записей). Задача - сравнить маленький с большим и выделить элементы, которые совпали в новый список.
Сначала я делал цикл в цикле, что было невероятно долго. Потом я отсотрировал оба списка и второй цикл уже проводился с номера последнего выхода. Таким образом время значительно сократилось. Теперь решил попробовать функцию Find, но что-то не получается.
Делаю примерно так:

Procedure  Poisk();
var FinderBl : Boolean;
   FinderInt: Integer;
   Raven:TStringList; // Список, куда попадут совпавшие элементы
Begin
Raven:=TStringList.create;
TSL.Sort;
TData.Sort;
TSL.Sorted:=True;
TData.Sorted:=True;

For i:=0 to TData.Count-1 do
  begin
     FinderBl:=TSL.Find(TData[i1],FinderInt);
     if FinderBl then Begin
        ShowMessage ("Ура!!! Есть!!!");
        Raven.Add(TData[i1]);
        end; // If      
  end; // For
end;

 TData- маленький список
 TSL - большой
К сожалению, после этой процедуры в Raven ничего не попадает и радостное сообщение ни разу не появляется. Хотя старинным методом цикла в цикле равенства выявлялись в 80% записей.
 Что я делаю не так?


 
Sandman25 ©   (2004-08-10 15:32) [1]

Нужно обойтись без циклов. Сдвигать указатель то в одном списке, то в другом.


 
Pavelkq   (2004-08-10 15:46) [2]

А можно наглядно? Я пока еще чайник:-(


 
Sandman25 ©   (2004-08-10 15:52) [3]

Первый список
1 2 3 6 8

Второй список
2 4 5 6 7 9

Имеем, что переменные указывают на
1
2
затем
2
2 - совпадение
затем
3
4
затем
6
4
затем
6
5
затем
6
6 - совпадение
затем
8
7
затем
8
9
затем
достигнут конец обоих списков, конец алгоритма


 
Pavelkq   (2004-08-10 16:02) [4]

Так это и есть мой старый алгоритм цикла. По первому списку все равно пробегаем в цикле. Еще проблема в том, что в малом списке могут быть элементы, которых нет во втором списке. Тогда сдвиг указателя обоих списков на 1 приведет к ошибке, т.е. через один в малом списке элеменn может совпасть в текущим в большом. Списки же из string-ов.


 
TUser ©   (2004-08-10 16:04) [5]

// Есть отсортированные Str1 и Str2
i:=0; j:=0;
while (i < Str1.Count) and (j < Str2.Count) do
if Str1.Strings[i] < Str2.Strings[j] then // ф-цию сравнения строк сам реализуй
inc (i)
else
if Str1.Strings[i] > Str2.Strings[j] then
inc (j)
else begin
// if Str1.Strings[i] = Str2.Strings[j] then begin
ResStr.Add(Str1.Strngs[i]);
inc (i); inc(j);
end;


 
Pavelkq   (2004-08-13 12:53) [6]

Большое спасибо! Даже не подозревал, что строковые переменные можно сравнить > или <. Отлично работает!


 
TUser ©   (2004-08-13 13:15) [7]

Чего? Их нельзя так сравнивать. Я же написал
ф-цию сравнения строк сам реализуй,
Т.е. надо написать свою процедуру или испаользовать готовую - AnsiCompareStr.


 
TUser ©   (2004-08-13 13:16) [8]

Хотя нет - действительно можно. А я и сам не знал :)


 
Думкин ©   (2004-08-13 13:16) [9]

> [7] TUser ©   (13.08.04 13:15)

Почему? Попробуй.


 
AlexSV   (2004-08-13 13:56) [10]

Кстати при использовании AnsiCompareStr можно обойтись вообще одной проверкой:

i:=0; j:=0;
while (i < Str1.Count) and (j < Str2.Count) do
case AnsiCompareStr(Str1.Strings[i], Str2.Strings[j]) of
-1: inc (i);
1: inc (j);
else
begin
ResStr.Add(Str1.Strngs[i]);
inc (i); inc(j);
end;
end;



Страницы: 1 вся ветка

Форум: "Основная";
Текущий архив: 2004.08.29;
Скачать: [xml.tar.bz2];

Наверх




Память: 0.46 MB
Время: 0.034 c
1-1092308272
Vasislisk
2004-08-12 14:57
2004.08.29
TMainMenu (item прижать к правому краю формы)


14-1092130410
СержК
2004-08-10 13:33
2004.08.29
Как корректно удалить компонент?


14-1091876726
begin...end
2004-08-07 15:05
2004.08.29
Mail.Ru


1-1092306192
Lera
2004-08-12 14:23
2004.08.29
Формы.


9-1084382986
Dimaxx
2004-05-12 21:29
2004.08.29
Раскраска текстуры





Afrikaans Albanian Arabic Armenian Azerbaijani Basque Belarusian Bulgarian Catalan Chinese (Simplified) Chinese (Traditional) Croatian Czech Danish Dutch English Estonian Filipino Finnish French
Galician Georgian German Greek Haitian Creole Hebrew Hindi Hungarian Icelandic Indonesian Irish Italian Japanese Korean Latvian Lithuanian Macedonian Malay Maltese Norwegian
Persian Polish Portuguese Romanian Russian Serbian Slovak Slovenian Spanish Swahili Swedish Thai Turkish Ukrainian Urdu Vietnamese Welsh Yiddish Bengali Bosnian
Cebuano Esperanto Gujarati Hausa Hmong Igbo Javanese Kannada Khmer Lao Latin Maori Marathi Mongolian Nepali Punjabi Somali Tamil Telugu Yoruba
Zulu
Английский Французский Немецкий Итальянский Португальский Русский Испанский