Java Programmieraufgabe

Hallo zusammen

Ich habe eine Programmieraufgabe zu lösen und konnte die Grundaufgabe schon mal aufstellen. Jetzt brauche ich noch die Erweiterte Aufgabe, die ich in die Grundaufgabe einbauen muss. Weiss jemand wie ich dies lösen kann?

Grundaufgabe
Anna lernt lesen. Um sie dabei zu unterstützen, darf sie bei der Gute-Nacht-Geschichte mitlesen.
Jeden Abend wird eine weitere Geschichte aus dem schier unendlich dicken Kinderbuch verwendet.
Um Anna nicht zu überfordern liest sie anfänglich nicht alles selbst. Zusammen mit ihrem Vater hat
sie folgende Methode entwickelt.
Am ersten Abend liest Anna das erste Wort der ersten Geschichte. Der Vater liest den Rest vor. An
den darauf folgenden zwei Tagen darf Anna jeweils zwei Wörter der beiden nächsten Geschichten
selbst lesen. An weiteren drei Tagen liest sie bereits je drei Wörter der Geschichte selbst.
An welchem Tag darf sie das erste Mal fünf Wörter lesen?
Wie viele Wörter darf Anna in der 23. Geschichte selbst lesen?
Schreiben Sie ein Programm, das obige beiden Fragen für beliebige Zahlen selbst löst:
a) In welcher Geschichte (also an welchem Tag) darf sie zum ersten Mal n Wörter lesen?
b) Wie viele Wörter darf Anna in der m-ten Geschichte (also am m-ten Tag) schon selbst lesen?

Erweiterte Aufgabe
Annas Vater möchte die maximale Anzahl an Tage, die es braucht, bis Anna ein zusätzliches Wort
lesen darf, begrenzen. Z.B soll Anna nicht länger als 6 Tage die gleiche Anzahl an Wörter
verwenden, bis sie ein zusätzliches Wort verwenden darf. Das Bedeutet, dass sie auch bei 7 Wörter
schon nach dem 6. Abend 8 Wörter verwenden darf und diese auch wieder nur 6 Abende.
Erweitern Sie Ihr Programm so, dass der Benutzer eine Begrenzung am Anfang angeben und dann
wie gewohnt die Eingabe für a) und b) tätigen kann. Das Programm soll dann mit der angegeben
Begrenzung wie beschrieben fortfahren. Gibt der Benutzer die Zahl 0 ein, soll die Begrenzung
ignoriert werden.

import java.util.Scanner;

/**
 * annalerntlesen Mein Projekt
 */

public class annalerntlesen {

public static void main(String[] args) {
	new annalerntlesen().top();
}

void top() {
	int wahl = menu(); // 1: Wörter rechnen 2: Tag rechnen
	if (1 == wahl) {
		woerterRechnen(); //Wörter rechnen
	} else {
		tagRechnen(); // Tag rechnen
	}
	sc.close();
}


void woerterRechnen() {
	System.out.println("Bitte Tag (Geschichte) Nummer eingeben: ");
	int tag = sc.nextInt();
	int woerter = woerterBerechnen(tag);
	if (1 == woerter) {
		System.out.println("Am ersten Tag kann Anna ein Wort selbst lesen.");
	} else {
		System.out.println("Am Tag " + tag + " kann Anna " + woerter + " Wörter selbst lesen.");
	}
}

void tagRechnen() {
	System.out.println("Bitte Anzahl Wörter eingeben: ");
	int woerter = sc.nextInt();
	int tag = tagBerechnen(woerter);
	if (1 == woerter) {
		System.out.println("Am ersten Tag kann Anna ein Wort selbst lesen.");
	} else {
		System.out.println("Am Tag " + tag + " kann Anna zum ersten Mal " + woerter + " Wörter selbst lesen.");
	}
}

int tagBerechnen(int eingegebeneAnzahlWoerter) {
	int tag = 1;
	int woerter = 1;
	int mal = 1; // zum sovielten Mal darf Anna gleich
					// viele Wörter lesen
	while (woerter != eingegebeneAnzahlWoerter) { // solange nicht erreicht
		tag = tag + 1;
		if (mal == woerter) {
			mal = 1;
			woerter = woerter + 1;
		} else {
			mal = mal + 1;
		}
	} // end while
	return tag;
}

int woerterBerechnen(int eingegebenerTag) {
	int tag = 1;
	int woerter = 1;
	int mal = 1; // zum sovielten Mal darf Anna gleich
					// viele Wörter lesen
	while (tag != eingegebenerTag) { // solange nicht erreicht
		tag = tag + 1;
		if (mal == woerter) {
			mal = 1;
			woerter = woerter + 1;
		} else {
			mal = mal + 1;
		}
	} // End while Schleife
	return woerter;
}

Scanner sc = new Scanner(System.in);

int menu() {
	System.out.println("Wörter aus Tag berechnen  [1]");
	System.out.println("Tag aus Wörtern berechnen [2]");
	int wahl = sc.nextInt();
	return wahl;
}

} // Ende

Bitte beachten:
Klassennamen im UpperCamelCase.

Erweiterte Aufgabe, Teilaufgabe A:
Es kann eine Begrenzung (oder 0) der an einem Tag gelesenen Wörter für [1] (Wörter aus Tag berechnen) eingegeben werden.
Bitte beachten:
Zeile 72, if…

import java.util.Scanner;

/**
 * annalerntlesen Mein Projekt
 */

public class AnnaLerntLesen {

    public static void main(String[] args) {
        new AnnaLerntLesen().top();
    }

    void top() {
        int wahl1 = menu1();
        int wahl2 = menu2(); // 1: Wörter rechnen 2: Tag rechnen
        if (1 == wahl2) {
            woerterRechnen(wahl1); // Wörter rechnen
        } else {
            tagRechnen(/*...*/); // Tag rechnen
        }
        sc.close();
    }

    void woerterRechnen(int wahl1) {
        System.out.println("Bitte Tag (Geschichte) Nummer eingeben: ");
        int tag = sc.nextInt();
        int woerter = woerterBerechnen(tag, wahl1);
        if (1 == woerter) {
            System.out.println("Am ersten Tag kann Anna ein Wort selbst lesen.");
        } else {
            System.out.println("Am Tag " + tag + " kann Anna " + woerter + " Wörter selbst lesen.");
        }
    }

    void tagRechnen() {
        System.out.println("Bitte Anzahl Wörter eingeben: ");
        int woerter = sc.nextInt();
        int tag = tagBerechnen(woerter);
        if (1 == woerter) {
            System.out.println("Am ersten Tag kann Anna ein Wort selbst lesen.");
        } else {
            System.out.println("Am Tag " + tag + " kann Anna zum ersten Mal " + woerter + " Wörter selbst lesen.");
        }
    }

    int tagBerechnen(int eingegebeneAnzahlWoerter) {
        int tag = 1;
        int woerter = 1;
        int mal = 1; // zum sovielten Mal darf Anna gleich
                     // viele Wörter lesen
        while (woerter != eingegebeneAnzahlWoerter) { // solange nicht erreicht
            tag = tag + 1;
            if (mal == woerter) {
                mal = 1;
                woerter = woerter + 1;
            } else {
                mal = mal + 1;
            }
        } // end while
        return tag;
    }

    int woerterBerechnen(int eingegebenerTag, int wahl1) {
        int tag = 1;
        int woerter = 1;
        int mal = 1; // zum sovielten Mal darf Anna gleich
                     // viele Wörter lesen
        while (tag != eingegebenerTag) { // solange nicht erreicht
            tag = tag + 1;
            if (mal == woerter) {
                mal = 1;
                if (wahl1 == 0 || woerter + 1 <= wahl1)
                    woerter = woerter + 1;
            } else {
                mal = mal + 1;
            }
        } // End while Schleife
        return woerter;
    }

    Scanner sc = new Scanner(System.in);

    int menu1() {
        System.out.println("Begrenzung oder 0?");
        int wahl = sc.nextInt();
        return wahl;
    }

    int menu2() {
        System.out.println("Wörter aus Tag berechnen  [1]");
        System.out.println("Tag aus Wörtern berechnen [2]");
        int wahl = sc.nextInt();
        return wahl;
    }

} // Ende

Ausgabe z. B.:

Begrenzung oder 0?
0
Wörter aus Tag berechnen  [1]
Tag aus Wörtern berechnen [2]
1
Bitte Tag (Geschichte) Nummer eingeben: 
5
Am Tag 5 kann Anna 3 Wörter selbst lesen.


Begrenzung oder 0?
2
Wörter aus Tag berechnen  [1]
Tag aus Wörtern berechnen [2]
1
Bitte Tag (Geschichte) Nummer eingeben: 
5
Am Tag 5 kann Anna 2 Wörter selbst lesen.

Teilaufgabe B müsste daraus herleitbar sein (zusätzliches Menü, Parameter einführen, etc.).

Wenn nicht, oder wenn ich den Satz der erweiterten Aufgabe falsch verstanden hab, bitte noch mal melden.

hth, Cyborg

Hallo Cyborg

Besten Dank für die Herleitung, dies hat mir sehr geholfen!
Bin noch ein Anfänger in Sache Java-Programmieren.

Beste Grüsse
Mare

Ich muss zugeben, ich habe gar nicht versucht, die Logik hinter dem Code zu verstehen. Ich würde es (wenn ich es so einfach wie möglich runterbreche) so schreiben:

int tagBerechnen(int eingegebeneAnzahlWoerter) {
    int tageGesamt = 0;
    for(int woerter = 1; woerter < eingegebeneAnzahlWoerter; woerter = woerter + 1) {
        for(int tag = 1; tag <= woerter; tag = tag + 1) {
            tageGesamt = tageGesamt + 1;
        }
    }
    return tageGesamt + 1;
}

int woerterBerechnen(int eingegebenerTag) {
    int tageGesamt = 0;
    for(int woerter = 1; true; woerter = woerter + 1) {
        for(int tag = 1; tag <= woerter; tag = tag + 1) {
            tageGesamt = tageGesamt + 1;
            if (tageGesamt == eingegebenerTag) {
                return woerter;
            }
        }
    }
}

Bei der zweiten Methode wundert mich, dass der Compiler versteht, dass das return mittendrin ausreicht. War defnititv nicht immer so.

Besten Dank für die unterschiedlichen Möglichkeiten.

@Landei Ich hab die Logik auch nicht verstanden. :rofl: … Aber ich antworte auch, wenn ich mir nicht sicher bin.

Edit: Ihr kennt das doch von mir: Ganz politikerlike, sicheres Auftreten bei völliger Ahnungslosigkeit…

Oder anders: Große Klappe und wenig dahinter… :frowning:

@CyborgBeta So sollten die Testergebnisse sein Könnt Ihr mir weiterhelfen?:

@Landei Entspricht deine Lösung ihrer Tabelle? Kann das gerade schlecht testen. Wenn ja, müsste man das noch iwie in ihren Code unterbringen. (= sprich: rewrite.)

@CyborgBeta
Man müsste es noch in meinen Code unterbringen. :slight_smile: Nur habe ich nicht eine Idee und auch nicht so Java vertraut.

@Mare19 Schreibe gerade vom Handy aus, also auf mich ist heute nicht zu zählen. :wink:

@CyborgBeta
Kein Problem kann auch morgen sein :slight_smile:

@Mare19 Auch heute bin ich noch mit Handy unterwegs, das erleichtert es nicht gerade. :wink:

Ich würde sagen: Doch. Es gibt nur zwei Möglichkeiten: Entweder, das return wird ausgeführt, oder die äußere Schleife läuft endlos weiter.

Zur letzten Nachfrage, mit den Tabellen: Was soll man dazu sagen? Soll man die bisher geposteten Alternativen ausprobieren und damit vergleichen?

Ich würde sagen: Dennoch. Denn imo war es tatsächlich nicht immer so… In C, ja. Aber in Java nich.

@CyborgBeta
Ja die Tabelle sollte mit der Ausgabe im Terminal übereinstimmen. Dann sollte such der Code stimmen, jetzt funktioniert es ja nicht sauber. Denkst du das return macht den Fehler?

Falls du morgen Zeit hättest würde es mir sehr weiterhelfen:) Bin noch nicht so mit Java vertraut, Danke!

Hier, probier das mal, das müsste jetzt stimmen:

import java.util.Scanner;

/**
 * AnnaLerntLesen Mein Projekt
 */

public class AnnaLerntLesen {

	public static void main(String[] args) {
		new AnnaLerntLesen().top();
	}

	void top() {
		int wahl1 = menu1();
		int wahl2 = menu2(); // 1: Wörter rechnen 2: Tag rechnen
		if (1 == wahl2) {
			woerterRechnen(wahl1); // Wörter rechnen
		} else {
			tagRechnen(wahl1); // Tag rechnen
		}
		sc.close();
	}

	void woerterRechnen(int wahl1) {
		System.out.println("Bitte Tag (Geschichte) Nummer eingeben: ");
		int tag = sc.nextInt();
		int woerter = woerterBerechnen(tag, wahl1);
		if (1 == woerter) {
			System.out.println("Am ersten Tag kann Anna ein Wort selbst lesen.");
		} else {
			System.out.println("Am Tag " + tag + " kann Anna " + woerter + " Wörter selbst lesen.");
		}
	}

	void tagRechnen(int wahl1) {
		System.out.println("Bitte Anzahl Wörter eingeben: ");
		int woerter = sc.nextInt();
		int tag = tagBerechnen(woerter, wahl1);
		if (1 == woerter) {
			System.out.println("Am ersten Tag kann Anna ein Wort selbst lesen.");
		} else {
			System.out.println("Am Tag " + tag + " kann Anna zum ersten Mal " + woerter + " Wörter selbst lesen.");
		}
	}

	int tagBerechnen(int eingegebeneAnzahlWoerter, int wahl1) {
		int tag = 1;
		int woerter = 1;
		int mal = 1; // zum sovielten Mal darf Anna gleich
						// viele Wörter lesen
		while (woerter <= eingegebeneAnzahlWoerter) { // solange nicht erreicht
			tag = tag + 1;
			if (mal == woerter || wahl1 != 0 && mal >= wahl1) {
				mal = 1;
				woerter = woerter + 1;
			} else {
				mal = mal + 1;
			}
		} // end while
		return tag - 1;
	}

	int woerterBerechnen(int eingegebenerTag, int wahl1) {
		int tag = 1;
		int woerter = 1;
		int mal = 1; // zum sovielten Mal darf Anna gleich
						// viele Wörter lesen
		while (tag != eingegebenerTag) { // solange nicht erreicht
			tag = tag + 1;
			if (mal == woerter || wahl1 != 0 && mal >= wahl1) {
				mal = 1;
				woerter = woerter + 1;
			} else {
				mal = mal + 1;
			}
		} // End while Schleife
		return woerter;
	}

	Scanner sc = new Scanner(System.in);

	int menu1() {
		System.out.println("Begrenzung oder 0?");
		int wahl = sc.nextInt();
		return wahl;
	}

	int menu2() {
		System.out.println("Wörter aus Tag berechnen  [1]");
		System.out.println("Tag aus Wörtern berechnen [2]");
		int wahl = sc.nextInt();
		return wahl;
	}

} // Ende

Ansonsten schreit alles nach Logarithmus, Anna lernt in der annähernd doppelten Zeit je ein Wort mehr. :wink:

1 „Gefällt mir“

@CyborgBeta
Wow besten Dank! Ich werde es morgen früh testen. Wünsche noch einen schönen Abend und nochmals Danke für deine Zeit! :slight_smile:

Davon ausgehend, dass die Funktionen von @Landei stimmen, hier auch noch die geschlossenen Formen:

private static int tagSimple(int i)
{
    // https://oeis.org/A000124
    int n = i - 1;
    return n * (n + 1) / 2 + 1;
}

private static int woerterSimple(int n)
{
    // https://oeis.org/A002024
    return (int) Math.floor(Math.sqrt(2 * n) + 0.5);
}    

:sunglasses:

1 „Gefällt mir“

Jetzt stellt sich die Frage, ob @Mare19 alles über den Haufen werfen sollte, und alles noch mal neu schreiben könnte…

@Mare19 Ist das eine Schulaufgabe (als Hausaufgabe)? Es ist eine Frage, welche Patterns man hier ansetzt…

(Btw. wenn du plaudern möchtest, kannst du mir auch eine PN senden :wink:)