|
|
| Посл.отвђт | Сообщенiе |
|
|
Дата: Сен 8, 2004 12:07:16 Заранее извиняюсь если тема немного не туда, но вроде под вынь32. Я из сети получаю пакет данных(обычный массив типа char*) и в нём надо найти кодовую последовательность.(например 55АА=) ). Причём код очень кретичен к скорости. (Сам знаю асм(но не очень хорошо), но надо писать на С++, поэтому наверно асмовская вставка). можно конечно банальным for'ом, но может есть решение поэлегантнее? Заранее спасибо |
|
|
Дата: Сен 8, 2004 13:00:11 под вынь не знаю под Dos что то вроде при условии что конец масива обозначается нулём - если иначе то придётся указывать размер масива - и прогонять через цикл massiv db 'asdsadktw452984523945orgj mm cas;',55h,0AAh
db 'fkhg dfmcssadax;sldk ma;dkadl; a;sdkfsa '
...
...
lea si,massiv ;si на указатель масива
NexSymbol:lodsb ;получаем в al символ
or al,al ;Код ноль?
jz ExitFind ;угу - сваливаем
cmp al,55h ;Первый символ нашей
;последовательности?
jnz NexSymbol ;неа - идём смотреть следующий
lodsb ;да наш - получаем следующий
cmp al,0AAh ;следующий наш?
jz Found ;ага - нашли
dec si ;нет - уменьшаем указатель
jmp NexSymbol ;дальше
ExitFind:
...
...
...
found:
....
....
....
|
|
|
Дата: Сен 8, 2004 13:04:24 · Поправил: Same или так
massiv db 'asdsadktw452984523945orgj mm cas;',55h,0AAh
db 'fkhg dfmcssadax;sldk ma;dkadl; a;sdkfsa '
...
...
lea si,massiv ;si на указатель масива
NexSymbol:lodsw ;получаем в ax пару символов
or al,al ;У поледнего код ноль?
jz ExitFind ;угу - сваливаем
cmp ax,0AA55h ;Это оно?
jz Found ;Да - сваливаем
dec si ;нет - уменьшаем указатель
jmp NexSymbol ;продолжить поиск
ExitFind:
...
...
...
found:
....
....
.... |
|
|
Дата: Сен 8, 2004 13:18:39 Спасибо!=) последний вариант мне особенно понравился!=)) Интересно, а за сколько он успеет просмотреть 20000 байт? (вопрос конечно глупый, но число тактов наверно приблезительно оценить можно) |
|
|
Дата: Сен 8, 2004 14:52:40 eXod Если искомая последовательность наверняка есть в массиве, то можно сделать короче и быстрее исключив проверку на окончание массива: lea esi,massiv ;esi на указатель масива
NexSymbol:lodsw ;получаем в ax пару символов
dec esi
cmp ax,0AA55h ;Это оно?
jne short NexSymbol ;Нет - продолжаем
ExitFind: ;Здесь окажемся когда найдено.
.... |
|
|
Дата: Сен 8, 2004 15:32:10 =) жаль вот только последовательности там может и не оказаться... Может кто подскажет как можно замерить время выполнения программы? хочу стравнить разные варианты на асм вставках и на чистом с++=) может если скорость будет выше то в итоге вообще оставлю только описание функций/классов, а всё тело буду реализовывать на асме.(полностью к сожалению не получиться, другим надо класс встраивать в свою программку на с++) |
|
|
Дата: Сен 8, 2004 16:06:40 Просили же вроде не тупой перебор в цикле. Для поиска подстрок в строке нормальные люди используют Боуера-Мура и его производные адаптированные для конкретного случая. Особенно заметен выигрышь на длинных подстроках. http://algolist.manual.ru/search/esearch/index.php |
|
|
Дата: Сен 8, 2004 16:06:51 · Поправил: zzzyab Как испытать на время ? - Делаеш тестовую прогу с большим циклом этой продседуры. Запускаеш в Soft-ice и там показывается время исполнения.Получается что строчные инструкции и смена адресации тормозные (не испльзуй lodsb и word адресацию). start: mov dword ptr [esi],eax inc esi cmp eax, '55AA' ; char je p1:1 inc esi inc esi inc esi jmp start p1: mov byte ptr [esi],al cmp al,'=' jne start |
|
|
Дата: Сен 8, 2004 16:26:03 2Dr.Golova огромное спасибо за ссылку!!!! 2zzzyab дык софтайс ещё поставить надо... но помниться после перехода с 9х на НТ(2000) у меня так и не получилось его нормально поставить=( (в смясле не софтайс для 9х, а для НТ... на 2000 не хотел вставать). Может можно как-то программно(то бишь кодом в самой программе)? |
|
|
Дата: Сен 8, 2004 16:41:32 eXod поиск по форуму: RDTSС |
|
|
Дата: Сен 8, 2004 17:00:05 Dr.Golova Получается тот, кто не использует алгоритм Боуера-Мура ненормальный? Для данного случая тогда может Алгоритм Сдвига-Или предпочтительней? Как раз для маленьких искомых последовательностей. По сравнению с Боуера-Мура он требует меньше времени как в худшем случае, так и в усредненном варианте. |
|
|
Дата: Сен 8, 2004 17:34:10 · Поправил: _Juicy Между прочим, поиск в строке реализован аппаратно - и по идее должен выполняться быстрее такой код:
_asm {
mov eax, 0AA55h
mov ecx, length ; в вордах!
mov edi, pArray
cld
repne scasw
setz al
mov fFound, al
}
|
|
|
Дата: Сен 8, 2004 20:10:27 _Juicy К примеру, у меня такая строка: pArray db AAh,55h,AAh,55h ... ;-) |
|
|
Дата: Сен 8, 2004 21:27:18 Верно :) Можно два раза прогнать, хотя тогда неизвестно, будет ли выигрыш в скорости. |
|
|
Дата: Сен 8, 2004 22:02:21 · Поправил: boozook Можно два раза прогнать зачем? просто нужно scasb использовать... Можно попробовать распараллелить процесс: in_str proc ;вход: ;edi - адрес строки ;ecx - длина строки ;выход: ;не найдено - ecx==FALSE ;найдено - ecx!=FALSE, edi указывает на 0xAA55 mov ax,0AA55h lea ecx,[edi+(ecx-1)-3] cmp edi,ecx jae eo_long @@: cmp [edi],ax je at0 cmp [edi+1],ax je at1 cmp [edi+2],ax je at2 cmp [edi+3],ax je at3 add edi,4 cmp edi,ecx jc @B ;достаточно больших циклов eo_long: add ecx,3 sub ecx,edi je eo_short @@: cmp [edi+ecx-1],ax ;не факт, что мы найдем первое! je atECX dec ecx jne @B eo_short: ret atECX: lea edi,[edi+ecx-1] ret at3: inc edi at2: inc edi at1: inc edi at0: ret in_str endp должно быть быстрее в разы,.. хотя не знаю как там scasb работает... |
|
Powered by miniBB 1.6 © 2001-2002
Время загрузки страницы (сек.): 0.064 |