yureckor если объединять например strcmp и strcmpi в одну, то ни та ни другая не будут оптимальными. Чем универсальнее, тем медленнее получится. И вызовы более громоздкие. За примером далеко ходить не надо: fpulib от Filiatreault из пакета масм: пока разберешься с передаваемыми параметрами, быстрее свой код написать , который к тому же и быстрее в разы окажется. К тому же универсальность может наложить ограничения на функциональность. А делать по принципу оболочки, вызывающей соответствующие различные ф-ции, имхо смысла нет. Только писать больше.
alpet strtok - это тот же instr, если его вызывать с параметром стартовой позиции, полученным от предыдущего вызова.
cresta Да у меня они на самом деле разные, просто вызов один. Так и запоминать короче, и код более гибкий (в твоем случае придется переходами вызывать разные процедуры, в моем изменить ключ в регистре). IMHO, потратить несколько тактов на разводку, но не парится самому гораздо лучше. >fpulib от Filiatreault ну это вобще чудная какая-то библиотека, мне опять же важна была скорость написания программы, я сделал FPU_work (наверно те, кто не любит макросы и дзенствует на fpu кодом аж икают когда его видят >inst и split у меня есть следующая процедура Код (Text): zameni_v_str lpsz_text:DWORD lpsz_cto:DWORD lpsz_nacto:DWORD Заменяет в строке (lpsz_text) все участки (lpsz_cto) на (lpsz_nacto). Если (lpsz_nacto)=0 то удаляет найденные участки. Пример: ... tx_1 db "%SystemRoot%\system32;", 0 db 256 dup(?) ... invoke zameni_v_str, OF tx_1, tx("%SystemRoot%"), tx("C:\WINXP") ... изменит строку tx_1 на 'C:\WINXP\system32;' По-моему, удобно.
yureckor Оболочку для развода по разным функциям/участкам функции можно добавить всегда Главное набрать побольше функциональности, т.е. какие функции могут понадобиться. strncpy - это strleft/strmid (по вкусу) strncmp и strncmpi - эту функциональность си-функций обеспечивают strcmp и strcmpi соответственно, т.к. они возвращают количество совпавших символов, достаточно сравнить eax с той длиной, которую надо проверить на совпадение. Чуть подробней функционал каждой функции расписан в аттаче. 1559100728__strlib.inc
>multicat Стек не обязательно чистить вручную,MASM: Код (Text): sloji_str_mnogo proto C :DWORD,:DWORD,:VARARG ... sloji_str_mnogo proc C n:DWORD,kuda:DWORD,x:VARARG ... sloji_str_mnogo endp сам делает правильный invoke: invoke sloji_str_mnogo, 3, ADDR tx_1, tx("a"), tx("b"), tx("c") А для того, чтоб число самому не считать, у меня макрос Код (Text): ;- m_str_add macro kuda, x:VARARG Local n n=0 % FOR arg, <x> n=n+1 ENDM IF n EQ 1 invoke sloji_str, kuda, x ELSE invoke sloji_str_mnogo,n, kuda, x ENDIF endm
invoke сделает очистку, просто есть ещё и call, поэтому такая оговорка. не знаю, сгодится этот исходник кому-либо? Делаю под свою конкретную задачу (максимум скорости при полном пренебрежении размером), поэтому некоторые фрагменты могут показаться странными Но если кому-то интересно, почему бы и нет.
Мдя Зачем функциональность процедуры описывать флагами? Их потом нужно будет разгребать условными переходами, или тебе скорость и размер совсем не важны? Вот процедура, которая не требует ни одного флага, обеспечивает больше функциональности (информации на выходе о сравниваемых строках), работает в три раза быстрее (98 против 292 тиков), меньше и просто наглядней Это регистрозависимое сравнение. Для регистронезависимого думаю разница будет ещё больше, я не смог помотреть этот случай, т.к. там вызывается некая inva_win CharLower, а этой процедуры нет, пришлось регистронезависимую часть закомментировать. P.S. Проверял на таких строках: str_1 db 'aaabbbcaccdddaeeeffafggaghhahiiiajjjkkaklalaalac',0 str_2 db 'aaabbbcaccdddaeeeffafggaghhahiiiajjjkkaklalaalaa',0 1338633707___cr_strcmp.txt
хы, век живи век учись- а я думал StrLen из masm32lib работает только с символами от 0 до 127, а она и с русскими действует Надо переделать свои на Код (Text): mov ebx,[eax] ; read first 4 bytes add eax,4 ; increment pointer lea ecx,[ebx-01010101h] ; subtract 1 from each byte not ebx ; invert all bytes and ecx,ebx ; and these two and ecx,80808080h вместо mov ecx, 0000000FFh test eax, ecx jz @@s22 test ebx, ecx jz @@s22 mov ecx, 00000FF00h test eax, ecx jz @@s23 test ebx, ecx jz @@s23 mov ecx, 000FF0000h ... CharLower - это Виндовая, просто макрос inva_win регистры не портит (кроме eax). Самому разбираться с таблицей по моему опасно, мало ли чего. Только в твоей не ясно, когда сравниваешь например "proba" и "probe", выдает-то 4
Ничего не перепутал ? В смысле какая строка первая, какая вторая Выдаёт (-4) для str_1 db "proba",0 str_2 db "probe",0 push offset str_2 push offset str_1 call cr_strcmp т.е. str_1 меньше, и совпадают первые 4 символа. Как и должно быть.
S_T_A_S_ Кстати, о птицах: конец unicode-строки это нулевой ворд по любому смещению от начала или по смещению, кратному 2-м? Что-то по этому вопросу ничего не найду Код (Text): db 44,04,4B,04,00,00 'фы' db 44,04,4B,00,00 'фK' Вторая строка правильная или нет?
Вторая строка неправильна: размер символа = 2 байта (соответственно, все символы расположены по смещению кратному 2м), а тут получается пол-символа.
Однако юникод довольно корявая весчь S_T_A_S_ Когда ты говорил о конвертации, о чем шла речь? Виндовые апи типа MultiByteToWideChar или другие способы?
Люди, потестите кому не лень, перевод в юникод. Программка в аттаче. Должен выводиться юникод-MessageBox с пятью строками: Код (Text): 0123456789!@#$%^&*()_+={}~?><":;][ abcdefghijklmnopqrstuvwxyz ABCDEFGHIJKLMNOPQRSTUVWXYZ абвгдеёжзийклмнопрстуфхцчшщьыъэюя АБВГДЕЁЖЗИЙКЛМНОПРСТУФХЦЧШЩЬЫЪЭЮЯ На ХР (без SP) вроде работает, на других не знаю, не на чем проверить 2012546859__GENERIC.exe
cresta Велосипед изобретаешь? MultiByteToWideChar и WideCharToMultiByte прекрасно справляются и с определением размера буфера под результирующую строку и с конвертированием.