FindLastString() »»» Letztes Vorkommen von Strings ermitteln

Hier könnt Ihr gute, von Euch geschriebene Codes posten. Sie müssen auf jeden Fall funktionieren und sollten möglichst effizient, elegant und beispielhaft oder einfach nur cool sein.
Benutzeravatar
AND51
Beiträge: 5220
Registriert: 01.10.2005 13:15

Beitrag von AND51 »

Hi Thorium!

Bitte! Ich poste solche Procs ja auch, um schnellere Versionen zu erhalten, also wenn von euch die jeweils vorhandenen Lösungen nochmals optimieren kann, wär das doch gut!

Ich kann zwar nur ein ganz kleines bisschen ASM, denke aber, wenn du es schaffst, wird das der Prozedur nen enormen Geschwindigkeitsschub geben.

Trotzdem liegt es oftmals an der Arbeitsweise. Hier ist es doch logisch, oder: Wenn ich den letzten String suche, sollte ich auch von hinten anfangen zu suchen :mrgreen:

Egal, wie weit du das mit ASM schaffst, meint ihr (alle) nicht, ddass es noch eine gute Idee wäre, CaseINsensivität einzubauen?
PB 4.30

Code: Alles auswählen

Macro Happy
 ;-)
EndMacro

Happy End
Benutzeravatar
ts-soft
Beiträge: 22292
Registriert: 08.09.2004 00:57
Computerausstattung: Mainboard: MSI 970A-G43
CPU: AMD FX-6300 Six-Core Processor
GraKa: GeForce GTX 750 Ti, 2 GB
Memory: 16 GB DDR3-1600 - Dual Channel
Wohnort: Berlin

Beitrag von ts-soft »

>> Ich kann zwar nur ein ganz kleines bisschen ASM
Braucht man nicht, nur Pointern statt PeekC, weil Peek und Poke sind nunmal
sehr lahm.
PureBasic 5.73 LTS | SpiderBasic 2.30 | Windows 10 Pro (x64) | Linux Mint 20.1 (x64)
Nutella hat nur sehr wenig Vitamine. Deswegen muss man davon relativ viel essen.
Bild
Benutzeravatar
AND51
Beiträge: 5220
Registriert: 01.10.2005 13:15

Beitrag von AND51 »

Ich hatte *Pointer.Character drin, aber da ich die jeweils nur 1x brauchte, hab ichse wieder rausgetan.

Also der Zugriff mit *pointer\c ist besser, meinste?
PB 4.30

Code: Alles auswählen

Macro Happy
 ;-)
EndMacro

Happy End
Benutzeravatar
ts-soft
Beiträge: 22292
Registriert: 08.09.2004 00:57
Computerausstattung: Mainboard: MSI 970A-G43
CPU: AMD FX-6300 Six-Core Processor
GraKa: GeForce GTX 750 Ti, 2 GB
Memory: 16 GB DDR3-1600 - Dual Channel
Wohnort: Berlin

Beitrag von ts-soft »

AND51 hat geschrieben: Also der Zugriff mit *pointer\c ist besser, meinste?
Nicht besser! Schneller ist er, immer und zu jederzeit.
PureBasic 5.73 LTS | SpiderBasic 2.30 | Windows 10 Pro (x64) | Linux Mint 20.1 (x64)
Nutella hat nur sehr wenig Vitamine. Deswegen muss man davon relativ viel essen.
Bild
Benutzeravatar
AND51
Beiträge: 5220
Registriert: 01.10.2005 13:15

Beitrag von AND51 »

Könntest du mir dann helfen, meinen Code mit Pointer zu bestücken? Komme hier nicht so recht voran. Eigentlich sollte es aber doch recht einfach sein...?!
PB 4.30

Code: Alles auswählen

Macro Happy
 ;-)
EndMacro

Happy End
Benutzeravatar
AND51
Beiträge: 5220
Registriert: 01.10.2005 13:15

Beitrag von AND51 »

Habs jetzt. So? Ich weiß nicht, aber ich finde, das macht keinen großen Unterschied, da die Pointer jedes Mal neu zusammengerechnet werden.
Die Testergebnisse sagen jedoch: Der Pointer-Code ist schneller! :o
Du hast Recht!
Die Geschwindigkeitsvorteile sieht man am deutlichsten, wenn man nach einem Teil-String sucht, der sich nicht nah am Ende des Strings befindet , sodass fast der gesamte String durchsucht werden muss.

Code: Alles auswählen

Procedure.l FindLastString(String$, StringToFind$)
	Protected n, i, l=StringByteLength(String$)-SizeOf(Character), l2=StringByteLength(StringToFind$)-SizeOf(Character)
	Protected *String.Character, *StringToFind.Character
	For n=l To 0 Step -SizeOf(Character)
		*String=@String$+n
		*StringToFind=@StringToFind$
		If *String\c = *StringToFind\c
			For i=0 To l2 Step SizeOf(Character)
				*String=@String$+n+i
				*StringToFind=@StringToFind$+i
				If *String\c <> *StringToFind\c
					Break
				EndIf
			Next
			If i = l2+SizeOf(Character)
				Break
			EndIf
		EndIf
	Next
	ProcedureReturn (n+SizeOf(Character))/SizeOf(Character)
EndProcedure


Debug FindLastString("Ich liebe PureBasic! Du auch?", "Ich")
PB 4.30

Code: Alles auswählen

Macro Happy
 ;-)
EndMacro

Happy End
Benutzeravatar
ts-soft
Beiträge: 22292
Registriert: 08.09.2004 00:57
Computerausstattung: Mainboard: MSI 970A-G43
CPU: AMD FX-6300 Six-Core Processor
GraKa: GeForce GTX 750 Ti, 2 GB
Memory: 16 GB DDR3-1600 - Dual Channel
Wohnort: Berlin

Beitrag von ts-soft »

AND51 hat geschrieben:Könntest du mir dann helfen, meinen Code mit Pointer zu bestücken?
Ja, könnte schon
AND51 hat geschrieben: Komme hier nicht so recht voran. Eigentlich sollte es aber doch recht einfach sein...?!
Ist es nicht, deshalb bleibts auch bei könnte, hab nämlich kaum Zeit und Lust.
Du schaffst das schon :mrgreen:
PureBasic 5.73 LTS | SpiderBasic 2.30 | Windows 10 Pro (x64) | Linux Mint 20.1 (x64)
Nutella hat nur sehr wenig Vitamine. Deswegen muss man davon relativ viel essen.
Bild
Benutzeravatar
AND51
Beiträge: 5220
Registriert: 01.10.2005 13:15

Beitrag von AND51 »

Danke für die Zuversicht! Ich habs auch geschafft. Und schneller ist das Ding wirklich! Sogar um ein vielfaches, aber diese Differenz sieht man am besten, wenn man lange Strings nimmt.

Ist der Code gut so? Oder noch verbesserbar? Ich habe ihn einfach 1:1 ersetzt, d. h. vor jedem PeekC() einfach die Pointer manuell zusammengerechnet und dann mit der Struktur\c gearbeitet.

Soll ich mal den ganzen Testcode auch noch posten? Dann könnt ihr die Geschwindigkeitsunterschiede selber sehen.
PB 4.30

Code: Alles auswählen

Macro Happy
 ;-)
EndMacro

Happy End
Benutzeravatar
al90
Beiträge: 1101
Registriert: 06.01.2005 23:15
Kontaktdaten:

Beitrag von al90 »

Hab gerade mal einen test mit CompareMemory() gemacht. Brachte aber
keinen schub und war in etwa mit AND's erste Routine gleich schnell.

So und jetzt hab ich kein bock mehr darauf. :mrgreen:
Benutzeravatar
AND51
Beiträge: 5220
Registriert: 01.10.2005 13:15

Beitrag von AND51 »

In wie fern hast du CompareMemory benutzt?
Oder hast du etwa auch eine Prozedur erstellt?
PB 4.30

Code: Alles auswählen

Macro Happy
 ;-)
EndMacro

Happy End
Antworten