Variablen-Übergabe an Prozedur
- hjbremer
- Beiträge: 822
- Registriert: 27.02.2006 22:30
- Computerausstattung: von gestern
- Wohnort: Neumünster
Dann erklärt mir das mal ???
Code: Alles auswählen
;-- PB 4.02
EnableExplicit
Procedure Aendere_String (*str.s)
; mit *str.s wird die Adresse des String-Deskriptors an die Prozedur übergeben
*str + " Welt12"
EndProcedure
Define text.s
text = "Hallo"
Aendere_String(@text)
Debug text
Code: Alles auswählen
Procedure Aendere_String1 (*str.s)
; mit *str.s wird die Adresse des String-Deskriptors an die Prozedur übergeben
*str + " Welt1"
EndProcedure
Define text.s
text = "Hallo"
Aendere_String1(@text)
Debug text
Purebasic 5.70 x86 5.72 X 64 - Windows 10
Der Computer hat dem menschlichen Gehirn gegenüber nur einen Vorteil: Er wird benutzt
grüße hjbremer
Der Computer hat dem menschlichen Gehirn gegenüber nur einen Vorteil: Er wird benutzt
grüße hjbremer
PureBasic versucht, den String an den Speicher @text anzuhängen. Da der Speicher @text den Pointer zu einem String und nicht den String enthält, klappt das nicht.
Schau hier:
Schau hier:
Code: Alles auswählen
Procedure Aendere_String1 (*str.s)
; mit *str.s wird die Adresse des String-Deskriptors an die Prozedur übergeben
*str + " Welt1"
EndProcedure
Define text.s{100}
text = "Hallo"
Aendere_String1(@text)
Debug text
Das ist ein anderer Variablentyp. Es ging mir nicht um Strings mit fester Länge. Es ging mir gerade um Strings mit variabler Länge und darum, dass PB sich automatisch um die Speicherverwaltung kümmert.Leonhard hat geschrieben:Code: Alles auswählen
Define text.s{100}
Ich habe jetzt noch einen anderen Thread im engl. Forum gefunden, wo aktuell das gleiche diskutiert wird.

Code: Alles auswählen
;-- PB 4.02
EnableExplicit
Procedure Aendere_String (*str.String)
*str\s + " Welt 12345678901234567890"
EndProcedure
Define text.String
text\s = "Hallo"
Aendere_String(@text)
Debug text\s
- hjbremer
- Beiträge: 822
- Registriert: 27.02.2006 22:30
- Computerausstattung: von gestern
- Wohnort: Neumünster
Hallo Leonhard
Du hast in deinem Code auch genügend Platz reserviert
und dann klappt es natürlich !
ich wollte mit meinem Beispiel vor allem zeigen das der letzte Code den Little John gepostet hat nur dann funktioniert, wenn der String, der addiert wird nicht zu groß ist.
PureBasic reserviert für Strings einen Speicherbereich der meistens etwas größer als die Zeichenkette ist und füllt den Rest mit Char-Null auf.
Erst wenn die Addition der beiden Zeichenketten größer als der reservierte Bereich wird, dann erst wird der neu gebildete String verschoben im Speicher.
Beweis:
man vergleiche die Adressen ! Beim zweitem Mal zuweisen ändert sich nur die Adresse von b$
Du hast in deinem Code auch genügend Platz reserviert
und dann klappt es natürlich !
ich wollte mit meinem Beispiel vor allem zeigen das der letzte Code den Little John gepostet hat nur dann funktioniert, wenn der String, der addiert wird nicht zu groß ist.
PureBasic reserviert für Strings einen Speicherbereich der meistens etwas größer als die Zeichenkette ist und füllt den Rest mit Char-Null auf.
Erst wenn die Addition der beiden Zeichenketten größer als der reservierte Bereich wird, dann erst wird der neu gebildete String verschoben im Speicher.
Beweis:
Code: Alles auswählen
a$="Hallo"
b$="Hallo"
c$="Hallo"
Debug @a$
Debug @b$
Debug @c$
a$="Hallo1"
b$="Hallo2222222222"
c$="Hallo12"
Debug @a$
Debug @b$
Debug @c$
Purebasic 5.70 x86 5.72 X 64 - Windows 10
Der Computer hat dem menschlichen Gehirn gegenüber nur einen Vorteil: Er wird benutzt
grüße hjbremer
Der Computer hat dem menschlichen Gehirn gegenüber nur einen Vorteil: Er wird benutzt
grüße hjbremer
- hjbremer
- Beiträge: 822
- Registriert: 27.02.2006 22:30
- Computerausstattung: von gestern
- Wohnort: Neumünster
Little John: ja und eher nein
das hängt eben davon ab wie lang die zu verkettenden Zeichen sind. Wenn Sie zusammen größer als 11 Bytes sind funktioniert es nicht mehr.
ich nehme mal an du willst eine Stringvariable übergeben, diese in der Prozedur ändern und im Hauptprogramm diese Änderung benutzen. Wie in den guten alten Zeiten z.B. unter QuickBasic. Das geht so einfach in PB aber nicht.
Hier ein Beispiel wie es geht:
Das funktioniert natürlich auch mit 3 oder 4 oder 5 Variablen, egal welchen Typ. Hauptsache der Typ von Peek und Poke stimmt.
Und die Experten würden nun wieder sagen uuuuhhh, das geht auch anders und schneller. Recht haben Sie !!!
das hängt eben davon ab wie lang die zu verkettenden Zeichen sind. Wenn Sie zusammen größer als 11 Bytes sind funktioniert es nicht mehr.
ich nehme mal an du willst eine Stringvariable übergeben, diese in der Prozedur ändern und im Hauptprogramm diese Änderung benutzen. Wie in den guten alten Zeiten z.B. unter QuickBasic. Das geht so einfach in PB aber nicht.
Hier ein Beispiel wie es geht:
Code: Alles auswählen
;-- PB 4.02
Procedure Aendere_String (*str)
;weise der lokalen Variablen den übergebenen Text zu
;diese Zeile muß sein
txt$=PeekS(*str)
;verändere die lokale Variable
txt$="HJ sagt " + txt$ + " und muß jetzt ins Bett"
;übergebe lokale Variable an Variable im Hauptprogramm
;und PB erledigt den Rest, soll heißen verschieben des Strings im Speicher
PokeS(*str, txt$)
EndProcedure
Define text.s
text = "Hallo"
Aendere_String(@text)
Debug text
Und die Experten würden nun wieder sagen uuuuhhh, das geht auch anders und schneller. Recht haben Sie !!!
Purebasic 5.70 x86 5.72 X 64 - Windows 10
Der Computer hat dem menschlichen Gehirn gegenüber nur einen Vorteil: Er wird benutzt
grüße hjbremer
Der Computer hat dem menschlichen Gehirn gegenüber nur einen Vorteil: Er wird benutzt
grüße hjbremer
Das heißt bei Dir funktioniert der Code nicht? Das überrascht mich jetzt. Bei mir funktioniert er einwandfrei, und die verketteten Strings sind ja zusammen 31 Zeichen lang. Auch mit noch längeren Strings geht es bei mir.hjbremer hat geschrieben:Little John: ja und eher nein
das hängt eben davon ab wie lang die zu verkettenden Zeichen sind. Wenn Sie zusammen größer als 11 Bytes sind funktioniert es nicht mehr.
Genau.hjbremer hat geschrieben:ich nehme mal an du willst eine Stringvariable übergeben, diese in der Prozedur ändern und im Hauptprogramm diese Änderung benutzen. Wie in den guten alten Zeiten z.B. unter QuickBasic.
Das finde ich sehr irritierend, zumal ich in der Hilfe kein Wort dazu gefunden habe.hjbremer hat geschrieben:Das geht so einfach in PB aber nicht.
Ich staune dass das geht. Denn das Programm POKEt ja an die Adresse von 'text' im Hauptprogramm. Dort waren aber nur 5 Byte Speicherplatz reserviert.hjbremer hat geschrieben:Hier ein Beispiel wie es geht:
Das funktioniert natürlich auch mit 3 oder 4 oder 5 Variablen, egal welchen Typ. Hauptsache der Typ von Peek und Poke stimmt.Code: Alles auswählen
;-- PB 4.02 Procedure Aendere_String (*str) ;weise der lokalen Variablen den übergebenen Text zu ;diese Zeile muß sein txt$=PeekS(*str) ;verändere die lokale Variable txt$="HJ sagt " + txt$ + " und muß jetzt ins Bett" ;übergebe lokale Variable an Variable im Hauptprogramm ;und PB erledigt den Rest, soll heißen verschieben des Strings im Speicher PokeS(*str, txt$) EndProcedure Define text.s text = "Hallo" Aendere_String(@text) Debug text
Und wie geht es anders und schneller?hjbremer hat geschrieben: Und die Experten würden nun wieder sagen uuuuhhh, das geht auch anders und schneller. Recht haben Sie !!!
Gruß, Little John
- hjbremer
- Beiträge: 822
- Registriert: 27.02.2006 22:30
- Computerausstattung: von gestern
- Wohnort: Neumünster
Hallo Little John:
anders geht es so
macht im Grunde dasselbe, gefällt mir aber nicht, wegen dem *str.s bei der Übergabe und beim Poke ist der Klammeraffe. Ist mir persönlich irgendwie nicht so einfach und klar genug.
PS: es muß x$="HJ"+... heißen wie im obigen Beispiel und nicht txt$="HJ"+... wie im gestrigen Beispiel. Gibt sonst irgendwann einen Memory-Fehler. Warum ? keine Ahnung !
schneller geht es so:
aber wenn so, dann finde ich, kann man die Variable prgv gleich als global definieren und braucht den ganzen Zeigerkram nicht.
anders geht es so
Code: Alles auswählen
;-- PB 4.02
Procedure Aendere_String (*str.s)
txt$= *str
x$="HJ sagt " + txt$ + " und muß jetzt ins Bett"
PokeS(@*str,x$)
EndProcedure
Define text.s
text = "Hallo"
Aendere_String(@text)
MessageRequester("Test", text)
PS: es muß x$="HJ"+... heißen wie im obigen Beispiel und nicht txt$="HJ"+... wie im gestrigen Beispiel. Gibt sonst irgendwann einen Memory-Fehler. Warum ? keine Ahnung !
schneller geht es so:
Code: Alles auswählen
;-- PB 4.02
Structure Programmvariablen
name1.s
name2.s
usw.l
EndStructure
prgv.Programmvariablen
Procedure Aendere_String (*prgv.Programmvariablen)
*prgv\name1="HJ sagt " + *prgv\name1 + " und muß jetzt ins Bett"
*prgv\name2="HJ sagt " + *prgv\name2 + " und muß jetzt ins Bett"
EndProcedure
prgv\name1="Blubb"
prgv\name2="Hello"
Aendere_String(prgv)
MessageRequester("Test", prgv\name1+#CR$+prgv\name2)
Purebasic 5.70 x86 5.72 X 64 - Windows 10
Der Computer hat dem menschlichen Gehirn gegenüber nur einen Vorteil: Er wird benutzt
grüße hjbremer
Der Computer hat dem menschlichen Gehirn gegenüber nur einen Vorteil: Er wird benutzt
grüße hjbremer
2hjbremer:
Das gleiche wie Dein letztes Beispiel -- aber in einer "schlankeren" Variante -- hatte ich ja auch schon gepostet:
http://www.purebasic.fr/german/viewtopic.php?p=153521#153521
Du meintest dazu:
Gruß, Little John
Das gleiche wie Dein letztes Beispiel -- aber in einer "schlankeren" Variante -- hatte ich ja auch schon gepostet:
http://www.purebasic.fr/german/viewtopic.php?p=153521#153521
Du meintest dazu:
... was ich nach wie vor bezweifle.wie lang die zu verkettenden Zeichen sind. Wenn Sie zusammen größer als 11 Bytes sind funktioniert es nicht mehr.
Gruß, Little John