"Christmas - the time to fix the computers of your loved ones" « Lord Wyrm

C Lotto Quicktipp

Bunny 13.01.2016 - 17:28 3933 13
Posts

Bunny

Addicted
Avatar
Registered: Oct 2002
Location: Austria
Posts: 525
Hallo!

Ich habe mal eine Frage an die C - Programmierer...

Habe hier in einer freien halben Stunde folgendes Programm geschrieben:

Kompilieren auf Linux wie folgt: gcc -Wall lotto.c -o lotto

Das Execute-File wie üblich auf Linux ausführen: ./lotto

Das Programm fragt wieviele Lottotipps ausgegeben werden sollen und wartet auf eine Eingabe:

Komischerweise funktioniert das aber nur für 7 Lottotipps... Also wenn ich weniger eingebe bzw. max. 7 funktionierts ohne probleme... Alles was mehr is geht nicht, sprich es kommen 7 raus und dann steht das Programm...
WARUM IS DAS SO !?!?! :D :D

Code: C
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#include <unistd.h>

#define TIPP 6		// Anzahl Zahlen eines Lotto Tipps
#define LOTTO_ZAHLEN 45	// zahlen in lotto
#define CHECK_IF_SET_COLUMN 2	// wird gebraucht um zu pruefen ob Zahl schon gezogen wurde

int main(){
	int zahlen[LOTTO_ZAHLEN][CHECK_IF_SET_COLUMN];	// Menge alle Lottozahlen 1-45
	int lottotipp[TIPP];				// generierter lotto tip
	int i,j;					// zaehl variablen
	int anzahl_tipps = 0;				//wieviele tipps sollen ausgegeben werden

	/* Array initialisieren mit Zahlhen 1-45 */
	for(i = 0; i < LOTTO_ZAHLEN; i++){
		zahlen[i][0] = i+1;
	}
	/* Index auf 0 initialiesren */
	for(i = 0; i < LOTTO_ZAHLEN; i++){
		zahlen[1][i] = 0;
	}
	printf("*----------------LOTTO MASCHINE!----------------*\n");
	printf("*\t\t\t\t\t\t*\n");
	printf("*Autor: XXXX\t\t\t\t*\n");
	printf("*Lotto Version 1.0\t\t\t\t*\n");
	printf("*\t\t\t\t\t\t*\n");
	printf("*\t\t\t\t\t\t*\n");
	printf("*-----------------------------------------------*\n");
	printf("Wieviel Tipps sollen gespielt werden?: ");
	scanf("%d", &anzahl_tipps);			// einelesen wieviele Tipps
	printf("\n\n\n");

	for(j = 0; j < anzahl_tipps; j++){
		int index = 0;
		int zufall = 0;
		printf("Tipp %i:\t\t", j + 1);
		for(i = 0; i < TIPP; i++){
			srand(time(NULL));
			while(zahlen[zufall][CHECK_IF_SET_COLUMN] == 1){
				zufall = rand() % 45;
			}
			zahlen[zufall][CHECK_IF_SET_COLUMN] = 1;
			lottotipp[index] = zufall + 1;
			printf("%i\t", lottotipp[index]);
			index++;
		}
		printf("\n");
		sleep(1);
	}
	printf("\n\n\n");
	return 0;
}
Bearbeitet von Bunny am 13.01.2016, 17:29

Bunny

Addicted
Avatar
Registered: Oct 2002
Location: Austria
Posts: 525
btw.. ich seh grad das sämtliche "\" Slashes entfernt worden beim konvertieren hier als Code Teil.. sollte alle wer das Programm kompilieren wollen müssen diese wieder eingefügt werden ..

z:b bei allen printf() aufrufen...

Obermotz

Fünfzylindernazi
Avatar
Registered: Nov 2002
Location: OÖ/RI
Posts: 5262
Debug mal ein bisschen in dein "zahlen"-Array rein - da ist der Hund drin ;)

Bunny

Addicted
Avatar
Registered: Oct 2002
Location: Austria
Posts: 525
im array ??? :D

also da hätte ich den Fehler am wenigesten vermutet.. muss ich mir mal anschaun


AHHHHH :) !!! ich weis schon :D ... ich stell dann der vollständigkeit den korrektierten code rein
Bearbeitet von Bunny am 13.01.2016, 18:04

Bunny

Addicted
Avatar
Registered: Oct 2002
Location: Austria
Posts: 525
ok geht schon.. nur sehe ich jetzt ein anderes Problem... Die erste Zahl ist immer 1... WARUM !? :D

was ich geändert habe ist, nach jeder Ausgabe eines Lottotipps die Zweite Spalte des Arrays wieder auf 0 gesetzt.. da ja sonst irgendwann alle Werte auf 1 sind und natürlich nix mehr macht...

irgendwie Logisch.. .7 Tipps x 6 Zahlen = 42 .. und dann sind alle zahlen natürlich aufgebraucht.. was auch bedeutet dass eine Zahl nicht in mehreren Tipps vorkommen konnte... :D

Aber wie bekomm ich das Problem mit erster Zahl = 1 hin ???

Code: C
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#include <unistd.h>

#define TIPP 6		// Anzahl Zahlen eines Lotto Tipps
#define LOTTO_ZAHLEN 45	// zahlen in lotto
#define CHECK_IF_SET_COLUMN 2	// wird gebraucht um zu pruefen ob Zahl schon gezogen wurde


int main(){
	int zahlen[LOTTO_ZAHLEN][CHECK_IF_SET_COLUMN];	// Menge alle Lottozahlen 1-45
	int lottotipp[TIPP];				// generierter lotto tip
	int i,j;					// zaehl variablen
	int anzahl_tipps = 0;				//wieviele tipps sollen ausgegeben werden

	/* Array initialisieren mit Zahlhen 1-45 */
	for(i = 0; i < LOTTO_ZAHLEN; i++){
		zahlen[i][0] = i+1;
	}
	/* Index auf 0 initialiesren */
	for(i = 0; i < LOTTO_ZAHLEN; i++){
		zahlen[1][i] = 0;
	}
	printf("*----------------LOTTO MASCHINE!----------------*\n");
	printf("*\t\t\t\t\t\t*\n");
	printf("*Autor: XXXX\t\t\t\t*\n");
	printf("*Lotto Version 1.0\t\t\t\t*\n");
	printf("*\t\t\t\t\t\t*\n");
	printf("*\t\t\t\t\t\t*\n");
	printf("*-----------------------------------------------*\n");
	printf("Wieviel Tipps sollen gespielt werden?: ");
	scanf("%d", &anzahl_tipps);			// einelesen wieviele Tipps
	printf("\n\n\n");

	for(j = 0; j < anzahl_tipps; j++){
		int index = 0;
		int zufall = 0;
		printf("Tipp %i:\t\t", j + 1);
		for(i = 0; i < TIPP; i++){
			srand(time(NULL));
			while(zahlen[zufall][CHECK_IF_SET_COLUMN] == 1){
				zufall = rand() % 45;
			}
			zahlen[zufall][CHECK_IF_SET_COLUMN] = 1;
			lottotipp[index] = zufall + 1;
			printf("%i\t", lottotipp[index]);
			index++;
		}
		for(i = 0; i < LOTTO_ZAHLEN; i++){
			zahlen[1][i] = 0;
		}
		printf("\n");
		sleep(1);
	}
	printf("\n\n\n");
	return 0;
}

PuhBär

Schau ned so genau
Avatar
Registered: Sep 2002
Location: .
Posts: 1201
Du setzt da die falsche Dimension des Arrays zurück und überschreibst den Stack bzw. wenn es gut geht die nachfolgenden lokalen Variablen.

Code: C
zahlen[1][i] = 0;
Müsste doch lauten

Code: C
zahlen[i][1] = 0;
Das kannst du dann gleich in der ersten for-loop machen.

Außerdem greifst du dann mit Index 2 auf diese Dimension zu, was auch nicht gültig ist, weil nur 0-1 erlaubt.
Bearbeitet von PuhBär am 13.01.2016, 18:43

Bunny

Addicted
Avatar
Registered: Oct 2002
Location: Austria
Posts: 525
yes!!! ... du hast recht.. jetzt passts !! :) DANKE

EdiT:: wobei .. es stimmt nicht ganz .. jetzt ist nur im 1. Tipp die 1 Zahl immer 1 :)
Bearbeitet von Bunny am 13.01.2016, 18:47

PuhBär

Schau ned so genau
Avatar
Registered: Sep 2002
Location: .
Posts: 1201
Die 2. Schleife weiter unten hat den selber Fehler mit den vertauschten Dimensionen.

Theoretisch kannst du dir die 2 Dimensionen im Array eigentlich schenken, und nur ein einziges Array mit 45 Elementen lassen, dass du zu Beginn auf 0 setzt. Kommt die Zahl, nimmst du Zahl - 1 als Index und setzt auf 1.

Die Zahl selbst brauchst du ja eigentlich nicht noch einmal abspeichern, da du sowieso immer Index und Zahl hin und her konvertierst.
Bearbeitet von PuhBär am 13.01.2016, 18:50

Bunny

Addicted
Avatar
Registered: Oct 2002
Location: Austria
Posts: 525
hmm.. hört sich gar nicht so blöd an... stimmt.. ich bastel mal ... :)

maverick81

Little Overclocker
Avatar
Registered: Dec 2002
Location: Stmk/GU
Posts: 128
du bekommst immer die 1 weil du bei jedem neuen Tip mit index 0 rein gehst

Code: C
int zufall = 0;
printf("Tipp %i:tt", j + 1);
for(i = 0; i < TIPP; i++)
{
	srand(time(NULL));
	while(zahlen[zufall][CHECK_IF_SET_COLUMN] == 1){
		zufall = rand() % 45;
	}

	zahlen[zufall][CHECK_IF_SET_COLUMN] = 1;
        lottotipp[index] = zufall + 1;
	printf("%it", lottotipp[index]);
	index++;
}

Du solltest
Code: C
zufall = rand() % 45;
immer auch vor der while loop ausführen um eine zufällige zahl zu bekommen, ansonnsten startest du jedesmal mit 0 und die sollte auch nicht benutzt sein.

Weiters greifst du dann auf die falsche Spalte zu, weil CHECK_IF_SET_COLUMN ist mit 2 definiert, d.h. aber auch es gibt nur 0 und 1.

Bunny

Addicted
Avatar
Registered: Oct 2002
Location: Austria
Posts: 525
Also, mittlerweile habe ich die zweite Dimension entfernt..

aber das mit srand() vor der while() zumachen bringt auch nichts...

Bunny

Addicted
Avatar
Registered: Oct 2002
Location: Austria
Posts: 525
jetzt hab ichs... funktioniert!!!

Code: C
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#include <unistd.h>

#define TIPP 6		// Anzahl Zahlen eines Lotto Tipps
#define LOTTO_ZAHLEN 45	// zahlen in lotto


int main(){
	int zahlen[LOTTO_ZAHLEN];	// Menge alle Lottozahlen 1-45
	int i,j;					// zaehl variablen
	int anzahl_tipps = 0;				//wieviele tipps sollen ausgegeben werden

	/* Array initialisieren mit Zahlhen 1-45 */
	for(i = 0; i < LOTTO_ZAHLEN; i++){
		zahlen[i] = 0;
	}
	printf("*----------------LOTTO MASCHINE!----------------*\n");
	printf("*\t\t\t\t\t\t*\n");
	printf("*Autor: XXXX\t\t\t\t*\n");
	printf("*Lotto Version 1.0\t\t\t\t*\n");
	printf("*\t\t\t\t\t\t*\n");
	printf("*\t\t\t\t\t\t*\n");
	printf("*-----------------------------------------------*\n");
	printf("Wieviel Tipps sollen gespielt werden?: ");
	scanf("%d", &anzahl_tipps);			// einelesen wieviele Tipps
	printf("\n\n\n");

	for(j = 0; j < anzahl_tipps; j++){
		printf("Tipp %i:\t\t", j + 1);
		int zufall = 0;
		for(i = 0; i < TIPP; i++){
			srand(time(NULL));
			do{
				zufall = rand() % 45 + 1;
			}while(zahlen[zufall] == 1);
			zahlen[zufall] = zufall + 1;
			zahlen[zufall] = 1;
			printf("%i\t", zufall);
		}
		for(i = 0; i < LOTTO_ZAHLEN; i++){
			zahlen[i] = 0;
		}
		printf("\n");
		sleep(1);
	}
	printf("\n\n\n");
	return 0;
}

jetzt kann ich belieb viele Tipps generieren.. Zahlen beginnen immer anders.


:)
Bearbeitet von Bunny am 13.01.2016, 20:04

Blaues U-boot

blupp, blupp
Avatar
Registered: Aug 2005
Location: Graz
Posts: 1537
srand sollte imho eine ebene herausgezogen werden. dann hat jeder tipp einen eigenen seed und nicht jede zahl.
Bearbeitet von Blaues U-boot am 13.01.2016, 20:14

that

Moderator
Hoffnungsloser Optimist
Avatar
Registered: Mar 2000
Location: MeidLing
Posts: 11326
Ich hab zum Vergleich mal schnell was in C++11 gebastelt...

Code: CPP
#include <iostream>
#include <algorithm>
#include <vector>
#include <cstdlib>

int main(int argc, char* argv[])
{
        std::vector<int> z(45);
        int n = 0;
        std::generate(z.begin(), z.end(), [&n]{ return ++n; });
        int nTips = std::max(1, atoi(argc > 1 ? argv[1] : "1"));
        srand(time(nullptr));
        for (int i = 0; i < nTips; ++i)
        {
                std::random_shuffle(z.begin(), z.end());
                std::sort(z.begin(), z.begin()+6);
                for (int n = 0; n < 6; ++n)
                        std::cout << z[n] << "\t";
                std::cout << std::endl;
        }
}

Compilieren:
Code:
g++ -o lotto --std=c++11 lotto.cpp

Beim Ausführen einfach die Anzahl der Tipps mitgeben:
Code:
./lotto 5

Wer hat nochmal gesagt, C++ und C sind eh fast das selbe? ;)

Generell sollte man vielleicht einen besseren Zufallszahlengenerator verwenden, z.B. mersenne_twister_engine.
Kontakt | Unser Forum | Über overclockers.at | Impressum | Datenschutz