Hi und erstmal herzlich Willkommen in der Delphi-Praxis
Als erstes möchte ich mal eine Sache loswerden: Dein Code ist scheußlich!
Klar, Du hast schon gesagt, dass Du kein großer Delphi-Programmierer bist und da Du mit Chromosomen zu tun hast, würde ich mal darauf tippen, dass Du auch kein Informatik-Student sein dürftest?
Jedenfalls beziehe ich mich nicht auf die Semantik oder Syntax (hab Deinen Code noch nicht näher gelesen), sondern allein auf die Optik. So hast Du hier sehr merkwürdig eingerückten Code gepostet, zudem scheint mir auch etwas viel Logik in dieser einen Methode zu stecken.
Hier solltest Du Dir dringen anschauen, was es für Mittel der Strukturierung gibt und wie man diese verwendet (Stichwort Procedure und Function).
Auch was das Einrücken angeht, so solltest Du dieses zu Strukturierung verwenden. Das macht den Code sehr viel einfacher lesbar und damit weniger Fehleranfällig. Vorallem werden aber auch Deine Korrektoren eine erhöhte Chance haben den Code einfach zu verstehen und das kann doch positive Auswirkungen auf die Note haben.
Exemplarisch könnten wir hier folgenden Abschnitt betrachten:
Delphi-Quellcode:
begin
randomize;
//Anmerkung: k muss kleiner oder gleich maxN sein.
Write ('Bitte geben sie die Anzahl der Populationen ein:');
Readln (N);
//Write('Bitte geben Sie die Groesse k der Teilpopulation an (max. ', maxN, '): ');
//ReadLn(k);
for s:=1 to N do begin
for j:=1 to 10 do begin
geno.chromosom1[j] := Random(2);
geno.chromosom2[j] := geno.chromosom1[j];
//Speichert, welche chromosomen noch nicht geändert wurden.
besucht[j] := false;
end;
//Gibt die Anzahl der stattfindenden Vertauschungen an, sprich die Allelfrequenz. Hier 0,5-->5 Vertauschungen
vertauschungen := 5; //später bei mehr oder weniger Vertauschungen :=random(10)+1
Vergleich den mal mit folgendem:
Delphi-Quellcode:
begin
randomize;
//Anmerkung: k muss kleiner oder gleich maxN sein.
Write ('Bitte geben sie die Anzahl der Populationen ein:');
Readln (populationCount);
//Write('Bitte geben Sie die Groesse k der Teilpopulation an (max. ', maxN, '): ');
//ReadLn(k);
// Kommentar was die Schleife macht
for i := 1 to populationCount do
begin
// Kommentar, was die Schleife macht
for j := 1 to 10 do
begin
geno.chromosom1[j] := Random(2);
geno.chromosom2[j] := geno.chromosom1[j];
//Speichert, welche chromosomen noch nicht geändert wurden.
besucht[j] := false;
end; // for j := 1 to 10
//Gibt die Anzahl der stattfindenden Vertauschungen an, sprich die Allelfrequenz. Hier 0,5-->5 Vertauschungen
vertauschungen := 5; //später bei mehr oder weniger Vertauschungen :=random(10)+1
Ich hoffe Du siehst da ein paar (positive) Unterschiede. Im zweiten Fall wurden z.B. ein paar Variablen (ansatzweise) umbenannt. Findet jmd. etwas wie N, wird garantiert keiner wissen, was diese Variable speichert! Auch bei Zählvariablen solltest Du möglichst zu Buchstaben ab i greifen, für die äußerste Schleife überlicherweise i, für die nächste innere j usw.
Hierachie sollte immer durch einrückung (Code steht einen Tabulator weiter rechts) angezeigt werden. Hier siehst Du dann einfach, was z.B. den beiden Schleifen zugeordnet ist. Das was auf der gleichen Hierachiestufe steht, sollte auch die selbe Einrückung haben.
Auch solltest Du einzelne Leerzeilen zwischen einzelnen Abschnitten lassen und nicht einen riesen Block leerer Zeilen einfügen. Eine Leerzeile reicht völlig aus um anzuzeigen, dass hier eine bestimmte Einheit endet und nun etwas anderes gemacht wird.
Zitat von
altesfossil:
Hi,
1. Die Chromosomensätze, die es mir liefert, sollen in einer Datei gespeichert werden, weil ich die zu einem späteren zeitpunkt wieder brauchen werde.
2. ich sollte diese Datei überprüfen können, sie sollte also z.b. mit dem texteditor oder excel lesbar sein.
An sich sind diese beiden Punkte kein Problem. Du kannst hier auf beliebige Textformate (insbesondere auch eigene Varianten) zurückgreifen. Für Excel empfiehlt es sich, dass Du
CSV-Dateien (Character Seperated Files) verwendest. Damit kannst Du die Datei direkt in Excel öffnen. Das Format ist denkbar einfach aufgebaut, jede Zeile in der Datei entspricht einer Zeile in der Tabelle. Die Zeile wiederum besteht aus Strings, die durch ein einfaches Trennzeichen (häufig Komma oder Semikolon) getrennt sind.
Code:
eintrag_1_1;eintrag_1_2;eintrag_1_3;...
eintrag_2_1;eintrag_2_2;eintrag_2_3;...
....
So sähe eine mögliche
CSV-Datei aus. Empfehlen würde ich sie Dir für Dein Problem allerdings nicht.
Zu den üblichen Verdächtigen, die hier noch in Frage kommen dürften dann Ini-Dateien und
XML-Dateien zählen. Für diese Formate gilt natürlich, dass sie sich nicht so schön in Excel anzeigen lassen. Der Vorteil an Ini-Dateien liegt darin, dass Delphi mit TIniFile und TMemIniFile bereits Kapselungen für dieses Format mitbringt. Dabei werden Datensätze in Sektionen abgelegt. Ein Datensatz besteht aus einem (für die Sektion) eindeutigen Schlüssel und einem Wert. Du kannst dann gezielt den Wert eines Datums auslesen/setzen, auf welche Du über die Sektion und den Schlüssel zugreifen kannst:
Code:
[Sektion1]
S1=Blubb
S2=Foo
[Sektion2]
s1=Blä
Hier könntest Du dann z.B. das Datum Sektion1, s1 auslesen und erhälst Blubb. Ist jetzt nur ein Beispiel, die Idee dürfte klar sein?!
Als letztes wie gesagt, bleibt noch
XML. Dieses Format setzt auf Auszeichnungen (so genannte Tags). Die Tags werden dabei durch spitze Klammern dargestellt. Jedes Tag, dass geöffnet wird, muss auch wieder geschlossen werden (was das heißt siehst Du schon im Beispiel!).
Der Vorteil an
XML ist, dass es mehr Strukturierung erlaubt als die anderen Formate. So können Tags beliebig geschachtelt werden, es darf aber nur ein oberstes Element geben:
Code:
<oberstesElement>
<Individuum name="Blubb">
<Teilpopulution>
<Genotyp>
<Chromosom1>
<Value>0</Value>
<Value>2</Value>
<Value>1</Value>
....
<Value>1</Value>
</Chromosom1>
<Chromosom2>
<Value>0</Value>
<Value>2</Value>
<Value>1</Value>
....
<Value>1</Value>
</Chromosom2>
</Genotyp>
<Genotyp>
<Chromosom1>
<Value>0</Value>
<Value>2</Value>
<Value>1</Value>
....
<Value>1</Value>
</Chromosom1>
<Chromosom2>
<Value>0</Value>
<Value>2</Value>
<Value>1</Value>
....
<Value>1</Value>
</Chromosom2>
</Genotyp>
<Teilpopulution>
</Individuum>
</oberstesElement>
Dieses Einrücken ist optional und soll nur die Lesbarkeit erhöhen. Die Idee ist halt, dass Du hier wieder eine Hierachie schaffst. Alles was zwischen dem öffnenden und schließenden Tag steht gehört zum jeweiligen Element. Ein Genotyp besteht hier z.B. aus den Tags Chromosom1 und Chromosom2. Diese stellen wiederum eigene Hierachien dar, denen 10 Value-Tags untergeordnet sind. Diese wiederum haben direkt einen Wert.
Der Vorteil von
XML ist, dass Du hier eine Menge Werkzeuge findest, die Dir die Arbeit mit ihnen erleichtern. So kannst Du gibt es
XML-Transformationen, die Dir zusammen mit einer solchen
XML-Datei eine andere (leichter lesbare) Sicht erzeugen (XSLT) und Du kannst auch die Wohlgeformtheit eines
XML-Dokuments prüfen (DTD oder
XML-Schema). Willst Du also nur solche Dateien als valide ansehen, bei denen jeder Genotyp genau zwei Choromosomen mit je 10 Werten zwischen 0 und 2 hat, dann kannst Du das leicht mit automatisch prüfen lassen.
Deswegen ist mein klarer Tipp an Dich, dass Du auf
XML zurückgreifst. Wie man mit
CSV-Dateien, Inis oder
XML arbeitet findest Du, wenn Du nach den Begriffen in der
DP suchst.
Zitat von
altesfossil:
3.es gibt N populationen, jede population hat eine bestimmte Anzahl k von Idividuen drin, z.b. 500. Jetzt soll nochmal ein array( teilpopulation) mit k Einträgen entstehen, welche k-mal den chromosomensatz von Population 1 beinhaltet, dann ein weiterer array mit dem chromosomensatz von Population 2, usw... bis N. Diese N arrays würde ich auch gerne in eine Datei schreiben. Auch diese Daten würde ich gerne überprüfen und ich muss sie später abrufen und umwandeln können. da die zu speichernden Records aus array[1..10] of integer bestehen, noch eine Frage: kann man diese einzelarrays auch in einen String[10] umzuwandeln? Wenn ja, wie geht das?
An sich ist die Antwort auf die letzte Frage auch die Antwort darauf, wie Du Text-Dateien erstellst (
XML, Ini und
CSV sind nur speziell formatierte Textdateien). Um aus einer Zahl einen String zu erzeugen wird Dir die Funktion IntToStr zur Verfügung gestellt. Diese ist in der
Unit SysUtils definiert (mit uses SysUtils einbinden!).
Ja, such einfach erstmal nach einem der Formate und schau Dir an, wie man mit ihnen arbeitet. Ggf. kannst Du natürlich jederzeit weiter nachfragen.
Gruß Der Unwissende