Das deutsche QBasic- und FreeBASIC-Forum Foren-Übersicht Das deutsche QBasic- und FreeBASIC-Forum
Für euch erreichbar unter qb-forum.de, fb-forum.de und freebasic-forum.de!
 
FAQFAQ   SuchenSuchen   MitgliederlisteMitgliederliste   BenutzergruppenBenutzergruppen  RegistrierenRegistrieren
ProfilProfil   Einloggen, um private Nachrichten zu lesenEinloggen, um private Nachrichten zu lesen   LoginLogin
Zur Begleitseite des Forums / Chat / Impressum
Aktueller Forenpartner:

Module Level zu groß
Gehe zu Seite 1, 2  Weiter
 
Neues Thema eröffnen   Neue Antwort erstellen    Das deutsche QBasic- und FreeBASIC-Forum Foren-Übersicht -> Allgemeine Fragen zu QBasic.
Vorheriges Thema anzeigen :: Nächstes Thema anzeigen  
Autor Nachricht
Coar



Anmeldungsdatum: 13.08.2013
Beiträge: 9
Wohnort: Dinslaken

BeitragVerfasst am: 13.08.2013, 15:43    Titel: Module Level zu groß Antworten mit Zitat

Hallo Community,

zunächst damit mir nicht gleich ein paar Fachbegriffe um die Ohren gehauen werden:

Mein Wissen zu Qbasic bezieht sich auf 20-25 Jahre altes selbstbeigebrachtes Basic, hab nie sonst etwas mit Programmieren gelernt und mich mit Qbasic seit 2-3 Monaten als eine Art Logik Puzzel beschäftigt.
Mein erstes Projekt war ein Fussball-Manager und hatte im Quellcode ca 3K Zeilen. Mein 2. Projekt ist nun ein Rollenspiel alla DSA und folgendes Problem trat bei knapp über 1000 Zeilen auf: "Module Level zu groß".

Dadurch das mein erstes Projekt aus wesentlich mehr Zeilen bestand schließe ich mal dass das "Module-Level" nicht oder nicht nur von der Anzahl geschriebenen Zeilen abhängt, aber wovon dann?

Ich nutze viele Variabeln in dem Programm und baue sie oft im Stiel: " xyz(x) " auf . Nur bei Variabeln wo x>10 ist verwende ich dem DIM Befehl(oder sollte man das bei allen machen??)

Es sind erst einige SUBs geschrieben, ich könnte wohl auch noch mehr vom Hauptprogramm in Subs packen, aber nicht soviel, dass ich genug Platz habe.

Als Unterschied zum Manager habe ich in dem Programm das erste mal mit READ-DATA-RESTORE gearbeitet um die Startwerte von Charakterklassen oder Monsterwerte einfacher greifbar zu machen....kann es damit zusammenhängen?

Grafiken oder Sound nutze ich aus Mangel an Wissen nicht, bei mir läuft ein ASCII Zeichen über eine Karte von ASCII Zeichen;-)

bestimmt weiß einer Rat von euch....


p.s. was mir gerade auffällt: ich habe die Variablenbereiche meist nicht eingeschränkt also meist SINGEL und nicht INTEGER oder LONG Variabeln genutzt...vielleicht macht das auch was aus?
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
RockTheSchock



Anmeldungsdatum: 04.04.2007
Beiträge: 131

BeitragVerfasst am: 13.08.2013, 16:29    Titel: Speicher Antworten mit Zitat

Es ist schon ewig her, dass ich mit QB programmiert habe. Wenn du Freebasic verwenden würdest, hättest du definitiv keine Speicherprobleme.

Ansonsten kannst du mal versuchen Arrays und Variablen mit Redim bzw '$DYNAMIC zu definieren. Einem QuickBasic Programm stehen nämlich nur einige 64KB Blöcke Speicher zur Verfügung. Für Strings ~30KB. Außerdem gibt es das Konzept der Module. Jedem Code Modul steht ein 64KB Block zur verfügung. Allerdings müssen zwischen den Modulen entweder über COMMON [SHARED] kenntlich gemacht werden oder aber über Function / Sub Parameter übergeben werden. Viele unerfahrene Programmierer nutzen schreiben auch oft redundanten Code weil sie kaum Prozeduren mit Parametern einsetzen.

http://www.antonis.de/qbkochbu/index.htm#frei

http://www.antonis.de/qbkochbu/index.htm#feld


Wenn du Freebasic mal probieren möchtest erhälst du hier im Forum sicher auch Unterstützung bei der Umstellung. Du könntest auch dein Programm mal in der Rubrik Projektvorstellungen hochladen. Sicher gibt es dann konstruktive Kritik!
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
dreael
Administrator


Anmeldungsdatum: 10.09.2004
Beiträge: 2457
Wohnort: Hofen SH (Schweiz)

BeitragVerfasst am: 13.08.2013, 19:26    Titel: Re: Module Level zu groß Antworten mit Zitat

Coar hat Folgendes geschrieben:
Ich nutze viele Variabeln in dem Programm und baue sie oft im Stiel: " xyz(x) " auf . Nur bei Variabeln wo x>10 ist verwende ich dem DIM Befehl(oder sollte man das bei allen machen??)

QB kennt noch kein OPTION EXPLICIT, dagegen bei FreeBasic ist das die Standardeinstellung. => Dann muss jede Variable immer deklariert werden (nicht nur Felder), was aber den grossen Vorteil hat, schon viele Fehler zur Kompilierzeit abzufangen.

Coar hat Folgendes geschrieben:
p.s. was mir gerade auffällt: ich habe die Variablenbereiche meist nicht eingeschränkt also meist SINGEL und nicht INTEGER oder LONG Variabeln genutzt...vielleicht macht das auch was aus?

Macht bei Felder viel aus! Integer belegt nur 2 Byte pro Element, während SINGLE 4 Bytes belegt. FreeBasic kennt sogar Byte als Datentyp, so dass der Compiler schlussendlich speicheroptimierten Code liefern kann.

Ansonsten unterliegt QB als klassische MS-DOS-Anwendung den berühmten Limiten des konventionellen Speichers sowie auch der Segmentiertung vom Intel 8088 (heutige CPUs emulieren diesen Real Mode übrigens nur noch!). FreeBasic dagegen nutzt den 32-Bit-Modus und damit die lineare Speicheradressierung, so dass theoretisch bis zu 4 GB RAM verwendet werden können.
_________________
Teste die PC-Sicherheit mit www.sec-check.net
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden E-Mail senden Website dieses Benutzers besuchen
Coar



Anmeldungsdatum: 13.08.2013
Beiträge: 9
Wohnort: Dinslaken

BeitragVerfasst am: 14.08.2013, 14:28    Titel: Antworten mit Zitat

Vorab: Danke für die Antworten!

Das mit der Deklaration der Felder/sonstigen Variabeln als INTEGER hat mal überhaupt nicht geklappt. Nachdem es keine Verbesserung über die Zuweisung mit DIM oder den COMMON SHARED Befehl gebracht hab, hab ich mir die Mühe gemacht per Hand jeder Variabel das % anzuhängen( immerhin ca 100 verschiedene Variabeln) auch ohne Erfolg.

Einzige Lösung die ich zZt sehe ist die Auslagerung als SUB. Bisher habe ich die zu übergebenen Variabeln immer eng definiert und war so stark eingeschränkt in der Nutzbarkeit einer SUB, da Feldvariabeln ja nicht übergeben werden können. Da hörte sich der COMMON SHARED Vorschlag gut an, leider klappt es scheinbar nicht mit STRING ARRAY-Variabeln funktioniert, oder ich bin nur zu blödzwinkern (Beispiel : namen$(x) soll übergeben werden. In der COMMON Shared Zeile kann ich das $ ja nicht anhängen, deshalb meckert Qbasic im Programm, dass die Dataentypen nicht übereinstimmen.

Gibt's hierfür eine Lösung?
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
RockTheSchock



Anmeldungsdatum: 04.04.2007
Beiträge: 131

BeitragVerfasst am: 14.08.2013, 15:14    Titel: Antworten mit Zitat

Coar hat Folgendes geschrieben:
Einzige Lösung die ich zZt sehe ist die Auslagerung als SUB.

Du kannst auch Arrays übergeben:
http://en.allexperts.com/q/Qbasic-Quickbasic-1623/2009/9/array-qbasic-function.htm

Leider können wir hier ohne den kompletten Quellcode nur spekulieren. Sicher ist, dass du keine Speicherprobleme mit Freebasic haben wirst. Am besten du speicherst deine BAS module innerhalb von QB nochmal im Text Format mit der Endung BAS ab. Dann kannst du sie auch extern öffnen.

Falls du weiter mit QB wurschteln möchtest. Grundsätzlich würde ich überhaupt keine $%! Zeichen benutzen sondern alles definieren mit
DIM variablennamen AS INTEGER|LONG|SINGLE|DOUBLE|STRING

Dann ist die Umstellung ggf. auf FreeBasic auch nicht mehr so schwer!

Hier ein Link auf Englisch zum Speichermanagment von QB.
http://support.microsoft.com/kb/45850/en-us
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
Coar



Anmeldungsdatum: 13.08.2013
Beiträge: 9
Wohnort: Dinslaken

BeitragVerfasst am: 14.08.2013, 16:23    Titel: Antworten mit Zitat

alleine hier verstehe ich schon in deinem Beispiel nicht warum er rundet:
"anArray%( i ) = rnd * 100"

ich dachte immer rnd gibt eine Kommazahl zwischen 0 und 1 aus, rundet er weil die Variabel eine integer ist??? Wenn ja nach welcher Methode?

Ich hab immer per int/cint gerundet weil ich dachte es muss so.

Aber das Beispiel hat mir die Erleuchtung gebracht dass ganze Felder übergeben werden können und nicht immer nur 1 Wert aus dem Feld.

Und die Deklaration der Variabeln für eine SUB kann ich mir sparen mit COMMON SHARED? Was muss ich bei der Benutzung dieses Befehles beachten? Weil wenn ich für zb "DIM x(100) as integer" definiere muss ich dann auch die Common Shared x() as integer definieren ?
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
RockTheSchock



Anmeldungsdatum: 04.04.2007
Beiträge: 131

BeitragVerfasst am: 14.08.2013, 16:44    Titel: Common Shared Antworten mit Zitat

siehe Doku zu COMMON SHARED
http://support.microsoft.com/kb/33712/en-us

Beispiel mit "Subscript out of range":
Module #1 Hauptmodul
Code:

   DECLARE SUB test()
   CALL test


Module #2
Code:

   REM $DYNAMIC            'will work if this is commented out
   DIM SHARED a(10,30,30)  'Im Nebenmodul wird ein REDIM oder dynamisches DIM von arrays niemals ausgeführt!!! Deswegen der Fehler!!!
   SUB test STATIC
      a(1,1,1) = 4           'Subscript out of range error
      PRINT a(1,1,1)
   END SUB




Funktionierende Version:
Das hier läuft, weil das gemeinsame Array im Hauptmodul definiert wird und in allen Modulen wo es benutzt wird mit COMMON SHARED freigegben wird
Module #1 Hauptmodul
Code:

   DECLARE SUB test()
   DECLARE SUB test2(a() AS INTEGER)

   REM $DYNAMIC
   COMMON SHARED a()  AS INTEGER  ' Reihenfolge erst COMMON
   DIM a(10,30,30) AS INTEGER           'dann DIM
 
   a(0,1,1) = 11
   CALL test
   CALL test2 a()


Module #2
Code:

   COMMON SHARED A()  AS INTEGER

   SUB test STATIC
      PRINT a(0,1,1)
      a(1,1,1) = 3
      PRINT a(1,1,1)
   END SUB



Module #3 als Array Übergabebeispiel ich hoffe das geht so
Code:

'Du brauchst den Parameter nicht "a" nennen, hauptsache die deklaration im Hauptmodul und hier sind gleich. Und du nutzt hier in der Prozedur den hier vergebenen Namen
   SUB test2(a() AS INTEGER) 
      PRINT a(0,1,1)
      PRINT a(1,1,1)
      a(1,1,1) = 4
      PRINT a(1,1,1)
   END SUB


Das mit den Parameternamen hat folgenden Hintergrund. Stell dir vor du hast ein Modul das bietet mehrere SUB zum sortieren von beliebigen Arrays, dann soll dieses Modul möglichst wiederverwendet werden können. Deshalb übergibt man eigentlich lieber Parameter als Variablen/Arrays global zur Verfügung zu stellen. In dem Zusammenhang sei noch BYREF und BYVAL zu beachten. Wenn man eine Variable in einer SUB ändern will muss man sie per BYREF übergeben mit BYVAL wird eine Kopie übergeben, sodass änderungen daran in der SUB nicht an das aufrufende Programm zurückgegeben werden. Komplexe Datentypen werden standardmäßig per BYREF übergeben.

Übrigens werden bei größeren Projekten alle DECLARE Anweisungen zu einem Modul in eine *.bi Datei gepackt. Und dann wird diese bi Datei in jedes bas modul eingebunden wo diese Prozeduren benötigt werden
'$INCLUDE: 'foobar.bi'


Zuletzt bearbeitet von RockTheSchock am 14.08.2013, 17:23, insgesamt 6-mal bearbeitet
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
nemored



Anmeldungsdatum: 22.02.2007
Beiträge: 4204
Wohnort: ~/

BeitragVerfasst am: 14.08.2013, 17:02    Titel: Antworten mit Zitat

Zitat:
ich dachte immer rnd gibt eine Kommazahl zwischen 0 und 1 aus, rundet er weil die Variabel eine integer ist??? Wenn ja nach welcher Methode?

Er errechnet mit RND*100 erst eine Gleitkommazahl von 0 bis 100 (aber kleiner als 100); diese wird dann in eine Integer-Variable gespeichert und muss daher gerundet werden. Üblicherweise werden Nachkommaanteile kleiner .5 abgerundet und Nachkommastellen größer .5 aufgerundet. Bei exakt .5 rundet FreeBASIC mathematisch (nicht kaufmännisch); was QBASIC da genau macht, kann ich nicht sagen.

Der Nachteil an der Codezeile ist, dass du jetzt Zufallszahlen von 0 bis 100 enthältst, und zwar mit einer Wahrscheinlichkeit von 0,5% für die 0, 0,5% für die 100, und mit je 1% die restlichen Zahlen. Meistens will man gleichwahrscheinlich alle Zahlen von 0 bis 99 bzw. von 1 bis 100; und dann kommt man auf die Befehlszeile
Code:
zufallszahl = INT(RND*100)      ' Zufallszahl von 0 bis 99; oder
zufallszahl = INT(RND*100) + 1  ' Zufallszahl von 1 bis 100

INT rundet immer ab, was in diesem Fall sinnvoller ist als die mathematische/kaufmännische Rundung.
_________________
Deine Chance beträgt 1:1000. Also musst du folgendes tun: Vergiss die 1000 und konzentriere dich auf die 1.
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
RockTheSchock



Anmeldungsdatum: 04.04.2007
Beiträge: 131

BeitragVerfasst am: 14.08.2013, 21:28    Titel: Soccer als Anschaungsbeispiel Antworten mit Zitat

Ich habe mir mal dein Soccer Projekt angeschaut. Wenn du jetzt ein Rollenspiel so schreibst, dann wirst du zwangsläufig mit QB an Grenzen stoßen. Erstmal sollte ein Modul kompiliert in einen 64KB Block passen. Das bedeutet technisch, der Quellcode eines Moduls sollte nicht größer als ~40kb sein.

Damit du deine größeren Programme warten und auch später noch verstehen kannst, gebe ich dir hier mal ein paar Tips zur Struktur und Formatierung

  • eine logische Einheit also eine SUB oder FUNCTION sollte nicht länger als 200 Zeilen sein.
  • Der Hauptmodul Code sollte möglichst kurz (50 Zeilen = 2 Seiten) sein und daraus die grobe Struktur des Programmes sofort ersichtlich werden
  • Doppelpunkte, um mehrere Befehle auf eine Zeile zu quetschen bitte vermeiden
  • Man sollte Code mit tabs einrücken. Unter Optionen-Bildschirm kannst du Tabs auf 3 Leerzeichen setzen. Bitte guck dich mal etwas um dazu

Was du im Soccer Programm gemacht hast ist eine Art Modulare programmierung aber nicht das was ich in meinem vorherigen Posts verdeutlichen wollte. Du erzeugst dort einzelne programme die du mit RUN aufrufst. Ich bin mir nicht sicher ob dir klar ist was mit Modulen eigentlich gemeint ist: Du fügst ein Neues Modul mit Datei - Datei erstellen ein. Danach kannst du mit F2 durch die Module wechseln.
Außerdem legst du eine include datei an mit allen Type, Common und Declares die du nacher in alle Module mit '$include einbindest.

Bei sehr sehr großen Projekten sollte zu jedem Modul (.bas) auch eine Include (.bi) Datei angelegt die alle Declares enthält. So kann man dann die in anderen Modulen nur die Declare's (Subs und Funktionen) einbinden die man dort braucht.

Statt DATA und READ zu nutzen könntest du dir ein Modul nur zum auslesen externer Daten / Dateien anlegen. Wenn ich was größers Programmiert habe mit QB hab ich folgendes gemacht.


Erst alle Module angelegt ohne Inhalt. Dann hab ich mir eine .bi datei gebastelt oder sogar mehrere die die Datenstruktur beinhaltet haben. Dann habe ich angefangen leere Prozeduren (SUBs / FUNCTIONs) anzulegen mit aussagekräftigen Bezeichnungen. Und dann habe ich erst richtig angefangen zu programmieren.
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
Coar



Anmeldungsdatum: 13.08.2013
Beiträge: 9
Wohnort: Dinslaken

BeitragVerfasst am: 14.08.2013, 23:49    Titel: Antworten mit Zitat

danke für die Hinweise, und JA mir ist definitiv nicht klar was modulare Programmierung heißtzwinkern ich schreibe beim Programmieren einfach drauf los und schau mal wo ich auskomme.
Bei dem Soccer Programm habe ich zwangsläufig mich zum ersten mal mit SUBs beschäftigt und da das nicht ausreichte mir unter den Befehlen welche rausgesucht mit der ich noch mehr Code auslagern kann, in dem Fall war es der RUN Befehl;-) Bin halt sehr unerfahren und lerne durch: Befehl unter Help raussuchen-was macht der- versuchen in ein Programm einzubauen. Da ich meist den technischen Hintergrund nicht kenne oder die Zusammenhänge mir erklären kann ist try and error mein Weg der Wahl;-)
Ganz am Anfang deiner Erklärungen dachte ich noch du meinst mit Module die einzelnen SUBs , höre aber jetzt raus dass es wohl einzelne .bas Dateien sind die irgendwie verknüpft sind.

p.s. : Wenn ich Qbasic offen hab finde ich unter "Datei" keinen Punkt Datei erstellen, den ich dann mit F2 hin und herwechseln kann. Kann nur Neu wählen und das öfnet ein neues Programm .
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
RockTheSchock



Anmeldungsdatum: 04.04.2007
Beiträge: 131

BeitragVerfasst am: 15.08.2013, 07:54    Titel: Antworten mit Zitat

Zitat:
mich mit Qbasic seit 2-3 Monaten als eine Art Logik Puzzel beschäftigt.

Sorry, aber ich schreibe scheinbar lieber anstatt richtig zu lesen.

Du benutzt den Interpreter QBasic und ich habe mich auf den Compiler QuickBasic 4.5 bezogen. QuickBasic hat zusätzliche Features. Es kann mehrere Module einbinden, EXE Dateien erzeugen und externe Libraries nutzen.

Zitat:
ich schreibe beim Programmieren einfach drauf los und schau mal wo ich auskomme.


Wenn du weiterhin QBASIC verwenden willst, vergiss das mit den Modulen und DECLARE und COMMON und $INCLUDE, aber nutze die Prozeduren und so wenig gosub wie möglich. Du kannst auch von innerhalb einer SUB eine andere aufrufen.

Hier mal ein kleines Beispiel ohne es zu testen:
Code:

SUB Init()
   SCREEN 13
   INPUT "Geben sie die Konfigurationsdatei an:"; file$
   LoadConfig file$
END SUB

SUB LoadConfig(configfile AS STRING)
'   OPEN configfile FOR RANDOM AS #1
'   ...
'  CLOSE #1
END SUB

SUB CreateCharacter(typ AS String, char as CharacterClass)
   PRINT "geben Sie den Namen Ihres"+ typ + "an: ";
   Input char.title
'   ...
END SUB

SUB CreateWorld()
END SUB

SUB MoveForward(char as CharacterClass)
END SUB

SUB RotateLeft(char as CharacterClass)
END SUB

SUB GenerateActions(char AS CharacterClass)
END SUB

SUB ControlNPCs()
   LOCATE 1, 1
   PRINT "NPC",
   FOR i% = LBOUND(npc) TO UBOUND(npc)
       GenerateActions npc(i%)
       PRINT i%; " ";
   NEXT
END SUB

SUB PlayGame()
Dim currentchar as Integer
currentchar =1
DO
   ControlNPCs
   skey$ = INKEY$
   IF LEN(skey$) = 1 THEN
        askey% = ASC(UCASE$(skey$))
        LOCATE 20, 1
        PRINT skey$; askey%; SPACE$(10)
   ELSE
        askey% = 0
   END IF

   SELECT CASE askey%
     CASE 87     'W
       MoveForward character(currentchar) 'Aktuellen Character nach vorne bewegen
     CASE 65     'A
       RotateLeft  character(currentchar) 'nach lnks drehen
     CASE 50     '2 Character auswählen
       currentchar = 2
     '...
   END SELECT
LOOP until askey% = 27 'mit Escape Verlassen
END SUB


'Hauptprogramm
TYPE CharacterClass
  title as STRING * 50
  height as Integer    'Größe in cm
  weight as Integer   'Gewicht in Kilo
  race AS INTEGER       
  x AS INTEGER        'Position
  y AS INTEGER
  d AS INTEGER        'Richtung
END TYPE

Dim SHARED welt(1 TO 100,1 TO 100) AS Integer
Dim SHARED character(1 TO 4) AS CharacterClass
DIM SHARED npc(100) AS CharacterClass

Init
CreateCharacter "Hauptcharacter", character(1)
CreateCharacter "2. Character", character(2)
CreateWorld
PlayGame


EDIT:
Ich habs jetzt mal getestet und etwas geändert damit es direkt lauffähig ist
EDIT:
Und nochmal die schleife angepasst und NPCs Steuerung eingefügt. Das soll an dieser Stelle erstmal reichen. Dieses Beispiel soll dir erstmal nur die Struktur verdeutlichen. Es gibt noch soviele Dinge an dieser Stelle die ich noch erzählen könnte z.B. CONST anten aber jetzt ist wirklich schluss! Und mit dem drauf los schreiben, ist gerade am anfang sehr gut! Bei zweiten Versuch wenn man ungefähr weiss wo die Richtung hingeht hilft es aber das Programm zu strukturieren.
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
Coar



Anmeldungsdatum: 13.08.2013
Beiträge: 9
Wohnort: Dinslaken

BeitragVerfasst am: 15.08.2013, 11:22    Titel: Antworten mit Zitat

Danke für deine Mühe auch wenn ich zugeben muss das der Ablauf des Programmes erstmal sehr unübersichtlich wirkt für einen Laien.

Da ich einige Befehle nicht kenne oder benutzt habe hier ein paar Fragen:

Zitat:
SUB CreateCharacter(typ AS String, char as CharacterClass)
PRINT "geben Sie den Namen Ihres"+ typ + "an: ";
Input char.title


Hier hast du nach Input char.title geschrieben obwohl die Variabel doch nur char heißen soll, warum?

Zitat:

Dim SHARED welt(1 TO 100,1 TO 100) AS Integer


Ich kannte DIM bisher mit einer Angabe (100) oder (1 to 100) was macht dann ein "," mit einer weiteren Angabe? sowas wie Länge*Breite*Höhe?
Wenn ja, kann man da auch einfach ein "DIM welt(1 to 10000)" draus machen?


Was ist der Sinn eines Type Befehles:

Zitat:
TYPE CharacterClass
title as STRING * 50
height as Integer 'Größe in cm
weight as Integer 'Gewicht in Kilo
race AS INTEGER
x AS INTEGER 'Position
y AS INTEGER
d AS INTEGER 'Richtung
END TYPE


Warum definiere ich nicht einfach jede Variabel in der DIM Zeile. und wenn ich dann wie du eine variabel mit CharacterClass definiere :

Zitat:
DIM SHARED npc(100) AS CharacterClass


...was ist denn dann der Typ der Variabel, oder bedeutet das dass nur Variabeln mit dem Typ "CharacterClass" z.b. mit "SWAP" umtauschbar sind?

Was genau ist denn der Unterschied zwischen "DIM SHARED" und "COMMON SHARED"? teilen nicht beide Befehle den SUBs mit dass die Variabeln dort auch genutzt werden??



Vieles sollte bestimmt routinemäßig zum Handwerkszeug gehören, also sry wenn ich blöd nachfrage. Ich beschränke mich gerade darauf zu verstehen was notwendig ist, um SUB-Routinen Werte übernehmen und übergeben zu lassen. Das scheint zumindest der Schlüssel für mein Ursprungsproblem zu sein, es wird dann wahrscheinlich nur nicht so elegant sein wie du die SUBs nutzt;-)
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
Elor



Anmeldungsdatum: 12.07.2013
Beiträge: 205
Wohnort: Konstanz

BeitragVerfasst am: 15.08.2013, 11:33    Titel: Antworten mit Zitat

@Coar: Zitat aus deiner Soccer-Anleitung
Zitat:
Beachte bei allen Zahlen: Qbasic zeigt die 0 vor dem Komma nicht an. Beispiel: 0.3 Mio Euro = .3 Mio Euro


Mit PRINT USING geht's.
Beispiel:
Code:

dim Mil as single
Mil = .3!
'ohne using
print Mil
'mit using
print using "##.##";Mil


Unter PRINT USING in der Online-Hilfe findest du mehr Informationen.
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
RockTheSchock



Anmeldungsdatum: 04.04.2007
Beiträge: 131

BeitragVerfasst am: 15.08.2013, 11:37    Titel: Antworten mit Zitat

Du kannst dir deinen Eigenen Variablen Type basteln und auf die einzelnen Felder darin zugreifen.

char.title
char.d
char.x usw. ' x-Position in der 2D Welt
char.y usw. 'y-Position in der 2D Welt


Stell dir die Welt als 2D Raster vor, mit x,y Koordinaten du legst fest wo oben und wo unten ist. aber nehmen wir mal an 1,1 ist unten links und 100,100 ist oben rechts dann kannst

mitte links z.B. mit welt(1,50) zugreifen
oder wenn du die größe der welt anpassen willst bzw. durch laden aus einer Datei dynamisch anpasst nutze UBOUND und LBOUND

Code:
welt(lbound(welt), ubound(welt,2) \ 2 )


Intern sind 2 Dimensionale Arrays 1 dimensional. Aber QB nimmt dir die Berechnung ab.
Code:
Dim welt1d(1 to 10000)
Dim welt2d(1 to 100, 1 to 100)


welt1d und welt2d brauchen den gleichen Speicherplatz
um auf die zweite stelle in der dritten reihe zuzugreifen:
welt1d(100*3+2+1) +1 weil das array bei 1 beginnt
welt2d(2,3)


COMMON SHARED (freigabe über Modulgrenze) macht mehr als DIM SHARED (Globale freigabe im einzelnen Modul).Da QBasic im gegensatz zu QuickBasic was du herunterladen könntest keine Module kennt brauchst du den Befehl nicht.
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
Coar



Anmeldungsdatum: 13.08.2013
Beiträge: 9
Wohnort: Dinslaken

BeitragVerfasst am: 15.08.2013, 12:04    Titel: Antworten mit Zitat

Elor , auch wenn ich es ein Stück weit besser gefunden hätte der Übersichtlichkeit halber den Hinweis beim Post des Soccer Mangagers zu lesen.... Danke;-)

Das hat mich schon immer gefuchst diese Darstellung der 0.zahlen.

bedeutet print using "##.##";Mil dass das Programm unabhängig vom Variablenwert nur die beiden Stellen vor und nach dem Komma darstellt?

Also aus 132.665 Mio= 32.66 macht?
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
nemored



Anmeldungsdatum: 22.02.2007
Beiträge: 4204
Wohnort: ~/

BeitragVerfasst am: 15.08.2013, 12:34    Titel: Antworten mit Zitat

Im Prinzip ja (aber nicht ganz wegen des Überlaufs). PRINT USING gibt einen Wert formatiert aus. In der eingebauten Hilfe von QBasic steht dazu bestimmt einiges drin; ansonsten kann ich dir unsere Referenz sehr ans Herz legen:
http://www.fb-referenz.de/PRINT%20USING
(bitte immer den Abschluss-Hinweis "Unterschiede zu QB" beachten)
_________________
Deine Chance beträgt 1:1000. Also musst du folgendes tun: Vergiss die 1000 und konzentriere dich auf die 1.
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
RockTheSchock



Anmeldungsdatum: 04.04.2007
Beiträge: 131

BeitragVerfasst am: 15.08.2013, 12:55    Titel: Antworten mit Zitat

nochmal was zu types:
Code:

'Du könntest schreiben

Dim chartitle(100) as String
Dim charx(100) as Integer
Dim chary(100) as Integer
Dim chard(100) as Integer
Dim charpropertysword(100) as Integer
Dim charpropertysjump(100) as Integer
Dim charpropertysduck(100) as Integer
'...

'Du kannst aber auch folgendes machen
Type PropertyClass
   sword as Integer
   jump as Integer
   duck as Integer   
   hp as Integer
 
End Type

Type CharacterClass
  title as STRING * 50
  height as Integer 'Größe in cm
  weight as Integer 'Gewicht in Kilo
  race AS INTEGER
  x AS INTEGER 'Position
  y AS INTEGER
  d AS INTEGER 'Richtung
  props as PropertyClass
End Type
Dim char(100) as CharacterClass


Den Unterschied merkst du dann wenn du Funktionen mit Parametern schreibst. Bei der ersten Version musst du irgendwann zwangsläufig alles shared machen müssen.

Bei der zweiten Version übergibst einen bestimmten char und kannst auf alle eigenschaften zugreifen und diese bearbeiten. z.B:

Code:

SUB battle2(c1 as char, c2 as char)
  if c1.props.sword > c2.props.sword then
     c2.props.hp = c2.props.hp-3
  else if c1.props.sword < c2.props.sword then
     c1.props.hp = c1.props.hp-3
  else
     c2.props.hp = c2.props.hp-1
     c1.props.hp = c1.props.hp-1
  end if
END SUB

battle2 char(1), char(88)



Interessant ist auch das Type in Types Prinzip als Beispiel eine Person und eine Firma beide haben eine Eigenschaft adresse die von der Struktur gleich ist (Ort, PLZ, Straße, Hausnummer). Ansonsten haben die nicht viel gemein. Du kannst aber den AdressType in beiden anderen Types für Person und Firma benutzen. d.h. du definierst den Type Adresse nur einmal. Benutzt es aber an vielen anderen Stellen. Wenn du eine SUB die mit 2 Adressen als Sub eine Route auf einer Karte berechnet, ist es Sicht dieser SUB egal ob die Adressen von Firma, Kunde, Person, oder sonstwas sind es sind halt adressen.


Wenn du eine Waffe und Kampfwerte in separaten Types hast, kannst du npcs und chars damit erweitern. Es ist egal in welcher Konstellation gekämpft wird, du brauchst einer Funktion nur Waffe und Werte übergeben.
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
dreael
Administrator


Anmeldungsdatum: 10.09.2004
Beiträge: 2457
Wohnort: Hofen SH (Schweiz)

BeitragVerfasst am: 15.08.2013, 17:16    Titel: Re: Soccer als Anschaungsbeispiel Antworten mit Zitat

RockTheSchock hat Folgendes geschrieben:
Ich habe mir mal dein Soccer Projekt angeschaut. Wenn du jetzt ein Rollenspiel so schreibst, dann wirst du zwangsläufig mit QB an Grenzen stoßen.

Vielleicht ist ein Verweis auf den Artikel

http://www.dreael.ch/Deutsch/BASIC-Knowhow-Ecke/Anfaengerfehler.html

aus meiner berühmten Sammlung hier wieder einmal angebracht.

In diesem Fall ist noch speziell wichtig, so wenig fest codierte Daten im Quellcode wie nur möglich, zu verwenden und stattdessen möglichst viel aus Dateien einzulesen.
_________________
Teste die PC-Sicherheit mit www.sec-check.net
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden E-Mail senden Website dieses Benutzers besuchen
nemored



Anmeldungsdatum: 22.02.2007
Beiträge: 4204
Wohnort: ~/

BeitragVerfasst am: 15.08.2013, 18:53    Titel: Antworten mit Zitat

Zitat:
In diesem Fall ist noch speziell wichtig, so wenig fest codierte Daten im Quellcode wie nur möglich, zu verwenden und stattdessen möglichst viel aus Dateien einzulesen.

was ja auch den zusätzlichen Vorteil hat (bei einem Interpreter nicht so entscheidend, bei einem Compiler schon eher), dass die Daten wie z. B. Angriffswerte der Gegner später modifiziert werden können, ohne dazu in den Quelltext eingreifen zu müssen.
_________________
Deine Chance beträgt 1:1000. Also musst du folgendes tun: Vergiss die 1000 und konzentriere dich auf die 1.
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
Coar



Anmeldungsdatum: 13.08.2013
Beiträge: 9
Wohnort: Dinslaken

BeitragVerfasst am: 17.08.2013, 12:27    Titel: Antworten mit Zitat

Mmmm auch wenn ich das mit den Types noch nicht wirklich verstanden hab,

(warum hat die Variabel sword mit c2.props.sword was zu tun? den genauen Aufbau wie sich welches type auf was bezieht und warum ist mir echt noch zu hoch)

habe ich beim DIM ein neues Problem:

Ich will z.b. die Variabel werte(100,10) als Integer definieren,
im Programm setzte ich dann eine Variabel z.b. x in das Feld ein ( werte(50,x) ) nur gibt er mir eine Fehlermeldung "außerhalb des zulässigen Bereiches". X kann aber nicht größer sein als 10 und ist als Integer definiert. Was läuft falsch?
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
Beiträge der letzten Zeit anzeigen:   
Neues Thema eröffnen   Neue Antwort erstellen    Das deutsche QBasic- und FreeBASIC-Forum Foren-Übersicht -> Allgemeine Fragen zu QBasic. Alle Zeiten sind GMT + 1 Stunde
Gehe zu Seite 1, 2  Weiter
Seite 1 von 2

 
Gehe zu:  
Du kannst keine Beiträge in dieses Forum schreiben.
Du kannst auf Beiträge in diesem Forum nicht antworten.
Du kannst deine Beiträge in diesem Forum nicht bearbeiten.
Du kannst deine Beiträge in diesem Forum nicht löschen.
Du kannst an Umfragen in diesem Forum nicht mitmachen.

 Impressum :: Datenschutz