mbshareat
جمعه 23 مهر 1389, 12:57 عصر
با سلام و خدا قوت :قلب:
فکر می کنم چنین سوالی قبلا تو سایت دیدم ولی پیداش نکردم.
یه تابع می خوام که محل یه رشته رو تو رشته دیگه بر گردونه و از ابتدای رشته نگرده بلکه از محل خاصی مثلا کارکتر دوم به بعد بگرده.(اگه (Pos(Position,SubString,String داشتیم دیگه سوال نمی کردم)
من یه جا برای خودم نوشتم که تابعی به نام PosEx در یونیت StrUtils داریم ولی دیدم نخیر نداریم!
من معادلی برای Instr توی VB می خوام.:لبخند:
می دونم که با استفاده از Pos می تونم خودم کدشو بنویسم اما می خوام خیلی سریع باشه و فکر نکنم کدی هم بنویسم سریع اجراشه(گرچه نمی دونم چطور می تونم کد بهینه و سریع بنویسم مثلا اول کارکترهای رشته بزرگ رو یکی یکی با کارکتر اول SubString مقایسه کنم بعد برم سراغ دومین کارکتر SubString یا ...:اشتباه:)
این تابع رو برای پیدا کردن رشته تو فایل پر تکرار می خوام.:لبخندساده:
لطفا اگه کسی تاعی سراغ داره یا حد اقل کد بهینه و سریع داره بذاره!:متفکر:
MohsenB
جمعه 23 مهر 1389, 21:41 عصر
سلام
من این راه رو بهتون پیشنهاد میکنم . هم کوتاهه هم سریع :
به این کد نگاه کنید :
Pos(SerText, Copy(MainText,Start,End)) + Start;
دیگه توضیحات هم معلومه .
امیدوارم کارتون راه بیفته .
_______________________________
ای صبا با تو چه گفتند که خاموش شدی
چه شرابی به تو دادند که مدهوش شدی
***
تو که آتش کده عشق و محبت بودی
چه بلا رفت که خاکستر خاموش شدی
________________________________
vcldeveloper
شنبه 24 مهر 1389, 00:32 صبح
من یه جا برای خودم نوشتم که تابعی به نام PosEx در یونیت StrUtils داریم ولی دیدم نخیر نداریم!
تابع PosEx در یونیت StrUtils وجود داره.
mbshareat
شنبه 24 مهر 1389, 12:23 عصر
با سلام و درود
جناب MohsenB (http://barnamenevis.org/forum/member.php?u=63752)
کد شما خوبه اما به نظرم کندترین راه باشه:بامزه:(ببخشید که رک حرف می زنم). خود دلفی مثالی زده که کارکتر موجود در محل رو تغییر می ده .من هم رشته رو از فایل گرفتم و کارکتر اول SubString رو در موقعیت تغییر دادم و به جستجو ادامه دادم.خوشبختانه مشکل سرعت هم پیدا نکردم.
جناب آقای کشاورز عزیز(جای شما تو تاپیکام خالی خالیه!!!)
بنده امتحان کردم StrUtils رو به Uses اضافه کردم ولی باز چنین تابعی رو نشناخت!:گریه:
(فکر کنم علتش قدیمی بودن نسخه دلفی من هست:متعجب:)
اگه ممکنه یونیت StrUtils رو برام بذارین!:خجالت:
(من دنبال چیزی که کارم رو راه بندازه گشتم ولی چیزی پیدا نکردم)
---
ديگران را ببخش، نه به اين علت كه آنها لياقت بخشش تو را دارند، به اين علت كه تو لياقت آن را داري كه آرامش داشته باشي.
vcldeveloper
شنبه 24 مهر 1389, 17:04 عصر
بنده امتحان کردم StrUtils رو به Uses اضافه کردم ولی باز چنین تابعی رو نشناخت!:گریه:
(فکر کنم علتش قدیمی بودن نسخه دلفی من هست:متعجب:)
امیدوارم هنوز در حال استفاده از نسخه های فسیل شده دلفی مثل دلفی 4 یا دلفی 5 نباشید!
(* ***** BEGIN LICENSE BLOCK *****
*
* The function PosEx is licensed under the CodeGear license terms.
*
* The initial developer of the original code is Fastcode
*
* Portions created by the initial developer are Copyright (C) 2002-2004
* the initial developer. All Rights Reserved.
*
* Contributor(s): Aleksandr Sharahov
*
* ***** END LICENSE BLOCK ***** *)
function PosEx(const SubStr, S: string; Offset: Integer = 1): Integer;
{$IFNDEF UNICODE}
asm
test eax, eax
jz @Nil
test edx, edx
jz @Nil
dec ecx
jl @Nil
push esi
push ebx
push 0
push 0
mov esi,ecx
cmp word ptr [eax-10],1
je @substrisansi
push edx
mov edx, eax
lea eax, [esp+4]
call System.@LStrFromUStr
pop edx
mov eax, [esp]
@substrisansi:
cmp word ptr [edx-10],1
je @strisansi
push eax
lea eax,[esp+8]
call System.@LStrFromUStr
pop eax
mov edx, [esp+4]
@strisansi:
mov esi, [edx-4] //Length(Str)
mov ebx, [eax-4] //Length(Substr)
sub esi, ecx //effective length of Str
add edx, ecx //addr of the first char at starting position
cmp esi, ebx
jl @Past //jump if EffectiveLength(Str)<Length(Substr)
test ebx, ebx
jle @Past //jump if Length(Substr)<=0
add esp, -12
add ebx, -1 //Length(Substr)-1
add esi, edx //addr of the terminator
add edx, ebx //addr of the last char at starting position
mov [esp+8], esi //save addr of the terminator
add eax, ebx //addr of the last char of Substr
sub ecx, edx //-@Str[Length(Substr)]
neg ebx //-(Length(Substr)-1)
mov [esp+4], ecx //save -@Str[Length(Substr)]
mov [esp], ebx //save -(Length(Substr)-1)
movzx ecx, byte ptr [eax] //the last char of Substr
@Loop:
cmp cl, [edx]
jz @Test0
@AfterTest0:
cmp cl, [edx+1]
jz @TestT
@AfterTestT:
add edx, 4
cmp edx, [esp+8]
jb @Continue
@EndLoop:
add edx, -2
cmp edx, [esp+8]
jb @Loop
@Exit:
add esp, 12
@Past:
mov eax, [esp]
or eax, [esp+4]
jz @PastNoClear
mov eax, esp
mov edx, 2
call System.@LStrArrayClr
@PastNoClear:
add esp, 8
pop ebx
pop esi
@Nil:
xor eax, eax
ret
@Continue:
cmp cl, [edx-2]
jz @Test2
cmp cl, [edx-1]
jnz @Loop
@Test1:
add edx, 1
@Test2:
add edx, -2
@Test0:
add edx, -1
@TestT:
mov esi, [esp]
test esi, esi
jz @Found
@String:
movzx ebx, word ptr [esi+eax]
cmp bx, word ptr [esi+edx+1]
jnz @AfterTestT
cmp esi, -2
jge @Found
movzx ebx, word ptr [esi+eax+2]
cmp bx, word ptr [esi+edx+3]
jnz @AfterTestT
add esi, 4
jl @String
@Found:
mov eax, [esp+4]
add edx, 2
cmp edx, [esp+8]
ja @Exit
add esp, 12
mov ecx, [esp]
or ecx, [esp+4]
jz @NoClear
mov ebx, eax
mov esi, edx
mov eax, esp
mov edx, 2
call System.@LStrArrayClr
mov eax, ebx
mov edx, esi
@NoClear:
add eax, edx
add esp, 8
pop ebx
pop esi
end;
{$ELSE}
asm
test eax, eax
jz @Nil
test edx, edx
jz @Nil
dec ecx
jl @Nil
push esi
push ebx
push 0
push 0
mov esi,ecx
cmp word ptr [eax-10],2
je @substrisunicode
push edx
mov edx, eax
lea eax, [esp+4]
call System.@UStrFromLStr
pop edx
mov eax, [esp]
@substrisunicode:
cmp word ptr [edx-10],2
je @strisunicode
push eax
lea eax,[esp+8]
call System.@UStrFromLStr
pop eax
mov edx, [esp+4]
@strisunicode:
mov ecx,esi
mov esi, [edx-4] //Length(Str)
mov ebx, [eax-4] //Length(Substr)
sub esi, ecx //effective length of Str
shl ecx, 1 //double count of offset due to being wide char
add edx, ecx //addr of the first char at starting position
cmp esi, ebx
jl @Past //jump if EffectiveLength(Str)<Length(Substr)
test ebx, ebx
jle @Past //jump if Length(Substr)<=0
add esp, -12
add ebx, -1 //Length(Substr)-1
shl esi,1 //double it due to being wide char
add esi, edx //addr of the terminator
shl ebx,1 //double it due to being wide char
add edx, ebx //addr of the last char at starting position
mov [esp+8], esi //save addr of the terminator
add eax, ebx //addr of the last char of Substr
sub ecx, edx //-@Str[Length(Substr)]
neg ebx //-(Length(Substr)-1)
mov [esp+4], ecx //save -@Str[Length(Substr)]
mov [esp], ebx //save -(Length(Substr)-1)
movzx ecx, word ptr [eax] //the last char of Substr
@Loop:
cmp cx, [edx]
jz @Test0
@AfterTest0:
cmp cx, [edx+2]
jz @TestT
@AfterTestT:
add edx, 8
cmp edx, [esp+8]
jb @Continue
@EndLoop:
add edx, -4
cmp edx, [esp+8]
jb @Loop
@Exit:
add esp, 12
@Past:
mov eax, [esp]
or eax, [esp+4]
jz @PastNoClear
mov eax, esp
mov edx, 2
call System.@UStrArrayClr
@PastNoClear:
add esp, 8
pop ebx
pop esi
@Nil:
xor eax, eax
ret
@Continue:
cmp cx, [edx-4]
jz @Test2
cmp cx, [edx-2]
jnz @Loop
@Test1:
add edx, 2
@Test2:
add edx, -4
@Test0:
add edx, -2
@TestT:
mov esi, [esp]
test esi, esi
jz @Found
@String:
mov ebx, [esi+eax]
cmp ebx, [esi+edx+2]
jnz @AfterTestT
cmp esi, -4
jge @Found
mov ebx, [esi+eax+4]
cmp ebx, [esi+edx+6]
jnz @AfterTestT
add esi, 8
jl @String
@Found:
mov eax, [esp+4]
add edx, 4
cmp edx, [esp+8]
ja @Exit
add esp, 12
mov ecx, [esp]
or ecx, [esp+4]
jz @NoClear
mov ebx, eax
mov esi, edx
mov eax, esp
mov edx, 2
call System.@UStrArrayClr
mov eax, ebx
mov edx, esi
@NoClear:
add eax, edx
shr eax, 1 // divide by 2 to make an index
add esp, 8
pop ebx
pop esi
end;
{$ENDIF}
vBulletin® v4.2.5, Copyright ©2000-1403, Jelsoft Enterprises Ltd.