Seite 3 von 5

Verfasst: 31.07.2007 17:54
von PureLust
ts-soft hat geschrieben:Ich denke er meint die IsFunktionen:
IsSprite, IsGadget, IsHübsch ...
Die sind schon wichtig bei dynamischen Sachen und in Callbacks
Achso ... ich hatte schon gehofft es gäbe was Neues bei den noch fehlenden Dingen wie:
IsScreen, IsStartDrawing, ScreenWidth, ScreenHeight etc.

Verfasst: 06.08.2007 02:45
von ReneMiner
Noch ein Array-Problemchen...

Ich möchte einen dynamischen StrukturArray innerhalb einer Struktur erstellen doch bei all meinen Dimensionierungsversuchen bekomme ich immer "Garbage to the End of the Line" um die Ohren geschmettert.

Konkretes Beispiel, um es etwas greifbarer zu machen verwend ich jetzt mal Schallplatten und Lieder

Code: Alles auswählen


 
Structure einLied
    Titel.s
    Interpret.s
    Länge.l
EndStructure

Structure eineSchallplatte
  AlbumName.s     
  nTitel.l ' Anzahl der Titel
  Lied.einLied[XXX]         
EndStructure

Global Dim Platte.eineSchallplatte(0) ;dies wäre ebenfalls ein Array
; den ich im Verlaufe des Programmes anpassen müssen würde 
; eine Liste wäre aber ungeeignet da ich die "Platten" über ihre
; Index-Nummern aufrufen will und muss 
Ich möchte nun gerne das Lied[XXX] unter Schallplatte dynamisch haben weil ja auf jeder Platte unterschiedlich viele Lieder - nämich nTitel - sein könnten - konkret gehts aber um bis zu einige tausend Unterschied so das ich nicht mit einer festen Obergrenze arbeiten kann (die wäre real irgendwo bei 1,6 Mio) -

(meine "echte" einLied-Structure würde keine Strings enthalten sondern bestünde nur aus doubles & longs - falls das einen Unterschied macht, in der Schallplatten-Structure hätt ich aber Strings die ich notfalls auch auf eine feste Länge festlegen könnte wenn das nötig wäre)

Wie muss ich das dimensionieren bzw. geht das überhaupt?

Verfasst: 06.08.2007 02:53
von Fluid Byte
Ich möchte nun gerne das Lied[XXX] unter Schallplatte dynamisch haben ...
Ist nicht. Arrays in Strukturen müssen feste Größen haben.

Verfasst: 06.08.2007 02:57
von ReneMiner
ups- seh schon...

Verfasst: 06.08.2007 02:57
von ts-soft
So einfach geht das nicht, bzw. ist auch garnicht zu empfehlen. XML wäre
einfacher und IMHO sinnvoller in diesem Fall
Prinzipiell kannste aber so vorgehen:

Code: Alles auswählen

Structure einLied
    Titel.s
    Interpret.s
    Laenge.l
EndStructure

Structure Schallplatte
  AlbumName.s     
  nTitel.l ; Anzahl der Titel
  *Lied.einLied[0]         
EndStructure

Dim Platte.Schallplatte(0)
Lieder = 10
Platte(0)\Lied = AllocateMemory(Lieder * SizeOf(einLied))
Später dann reallokieren. Aber ich denke mal das Du ein MemoryLeak
haben wirst, weil PB die Strings in einLied nicht freigeben wird. Wenns
aber ein FixString auch tun sollte, wäre das auch kein Problem.

Trotzdem, lieber XML

Thomas

Verfasst: 06.08.2007 03:12
von Fluid Byte
Obwohl.....

Code: Alles auswählen

Structure einLied
	Titel.s
	Interpret.s
	Laenge.l
EndStructure

Macro Schallplatte(Elemente)
	Structure eineSchallplatte
		AlbumName.s     
		nTitel.l
		Lied.einLied[Elemente]         
	EndStructure
EndMacro

Schallplatte(10)

Global Dim Platte.eineSchallplatte(0)

Verfasst: 06.08.2007 03:15
von ReneMiner
na wie schon gesagt das mit den Liedern ist nur ein Beispiel, einLied hätte keine Strings sondern bestünde aus ner festen Anzahl von Doubles und Longs die Länge von einLied in Bytes wäre immer gleich.

Ich würde ja eigentlich gerne ungefähr so

Platte(1)\Lied[1]\Länge = 123

an meine Lied-Daten kommen.

...na mal kucken ob ich das hinkriege mit den Zeigern oder ob ich dabei den Rechner sprenge ...

EDIT:
:mrgreen: Fluid- das sieht gut aus.. danke
somit hätte jede Platte wohl ihre eigene Struktur.
Aber: was ist wenn ich da 5000 mal oder mehr durchlaufe- jeweils mit ner anderen Anzahl von Elementen? Ist der Speicher dann nicht voll? Wird die "alte" Structure eineSchallplatte nicht durch die neue zerstört

Verfasst: 06.08.2007 03:17
von ts-soft
Fluid Byte hat geschrieben:Obwohl.....
Wo ist die Dynamic? Das funktioniert nur einmal :wink:

@ReneMiner
Solange Du keine normalen Strings nimmst, sollte mein Code problemlos
laufen, tut er auch mit Strings, aber PB räumt den Speicher nicht korrekt auf.

Du kannst nacherher ganz normal auf das Array zugreifen, von 0 - ...

Verfasst: 06.08.2007 03:36
von Fluid Byte
ts-soft hat geschrieben:
Fluid Byte hat geschrieben:Obwohl.....
Wo ist die Dynamic? Das funktioniert nur einmal :wink:
Natürlich ist es dynamisch. Er kann die Menge eines Strukur-Arrays variabel setzen. Ohne Makro würde das nicht gehen. Außerdem setze ich natürlich voraus das er weiss das man eine Struktur nur einmal deklariert.

Verfasst: 06.08.2007 03:36
von edel
Das geht auch mit der ObjectLib von pb , wobei es weniger fuer Anfaenger
geeignet ist.

Code: Alles auswählen

Import "ObjectManager.lib"
   PB_Object_GetOrAllocateID(*Object,id.l) 
   PB_Object_EnumerateStart(*Object)
   PB_Object_EnumerateNext(*Object,*id)
   PB_Object_FreeID(*Object, DynamicOrArrayID.l)
   PB_Object_Init(StructureSize.l, IncrementStep.l, FreeID)  
EndImport 

Prototype SYS_FreeString(string.s)

Global SYS_FreeString.SYS_FreeString
!MOV [v_SYS_FreeString],_SYS_FreeString@4

Macro ForEachObject(obj,cursor)
   PB_Object_EnumerateStart(obj) 
   While PB_Object_EnumerateNext(obj,@cursor) 
EndMacro
;- 
Macro NextObject
   Wend 
EndMacro

; TEST

Structure Track
   title.s
   interpret.s
   laenge.l
EndStructure

Structure Schallplatte 
   name.s
   nTitel.l
   TitleObjListe.l
EndStructure

Global OblatenCD_Obj.l = PB_Object_Init(SizeOf(Schallplatte),10,0)

;- 
Procedure NeueSchallplatte(name.s,Titelanzahl)
   Protected *schallpladde.Schallplatte
   
   *schallpladde               = PB_Object_GetOrAllocateID(OblatenCD_Obj,#PB_Any)
   *schallpladde\name          = name
   *schallpladde\nTitel        = Titelanzahl
   *schallpladde\TitleObjListe = PB_Object_Init(SizeOf(Track),10,0)
   
   ProcedureReturn *schallpladde 
   CreateImage(0,0,0); dummy fuer simplelib
EndProcedure

;- 
Procedure LiedEinfuegen(*schallpladde.Schallplatte,interpret.s,title.s,laenge.l)
   Protected *lied.Track
   
   *lied = PB_Object_GetOrAllocateID(*schallpladde\TitleObjListe,#PB_Any)
   
   *lied\title     = interpret
   *lied\interpret = title
   *lied\laenge    = laenge
   
   ProcedureReturn *lied
EndProcedure

;- 
Procedure LeereSammlung()
   Protected *schalldings.Schallplatte
   Protected *titledings.Track
   
	ForEachObject(OblatenCD_Obj,*schalldings) 
      SYS_FreeString(*schalldings\name) 
      ForEachObject(*schalldings\TitleObjListe,*titledings)
         SYS_FreeString(*titledings\title)
         SYS_FreeString(*titledings\interpret)
         PB_Object_FreeID(*schalldings\TitleObjListe,*titledings)
      NextObject 
      PB_Object_FreeID(OblatenCD_Obj,*schalldings)
   NextObject 
EndProcedure

;-
   
SP = NeueSchallplatte("13 Mann und ein Kapitän",2)
LiedEinfuegen(SP,"HEINO","13 MANN UND EIN KAPITÄN",250)
LiedEinfuegen(SP,"HEINO","JENSEITS DES TALES",450)

SP = NeueSchallplatte("Wenn die bunten Fahnen wehn`n",2)
LiedEinfuegen(SP,"HEINO","Wenn die bunten Fahnen wehn`n",334)
LiedEinfuegen(SP,"HEINO","Wenn Dir alle Untreu werden",123)


ForEachObject(OblatenCD_Obj,*schalldings.Schallplatte)
   Debug *schalldings\name
   Debug ""
   ForEachObject(*schalldings\TitleObjListe,*titledings.Track)
      Debug "     " + *titledings\title.s
      Debug "     " + *titledings\interpret.s
      Debug "     " + Str(*titledings\laenge)
      Debug ""
   NextObject 
   Debug "-----------------------------"  
NextObject

LeereSammlung()
@Fluid Byte
Das ist nicht dynamisch , da du nur einen Konstanten Wert angeben
kannst, dafuer braucht man dann aber auch kein Macro