verstehe CharAt-Methode nicht...Eingabe mehrstelliger Zahlen

Ich habe ein Programm geschrieben, dass eine ISBN-Nummer auf ihre Korrektheit prüfen soll. Das geht über die Prüfziffer...mein Programm funktioniert richtig, nur muss ich wegen des Integer.parseInt Leerzeichen bei der Eingabe lassen...ich würde aber gern statt
z.b 9 7 9 3 1 3 7 8 1 3 6 5 5
direkt die Nummer in der Form
979-3-1378-1365-5 eingeben...ich bin auf den Befehl charAt gestoßen, aber ich habe erst angefangen und verstehe einfach nicht, wie das funktionieren soll. oder gibt es vielleicht noch einen anderen, einfacheren Weg?

Code:
public class Neu  {
     public static void main(String[] args)    {


	int stelle1  = Integer.parseInt(args[0]);
        int stelle2  = Integer.parseInt(args[1]);
        int stelle3  = Integer.parseInt(args[2]);
	int stelle4  = Integer.parseInt(args[3]);
	int stelle5  = Integer.parseInt(args[4]);
	int stelle6  = Integer.parseInt(args[5]);
	int stelle7  = Integer.parseInt(args[6]);
	int stelle8  = Integer.parseInt(args[7]);
	int stelle9  = Integer.parseInt(args[8]);
	int stelle10 = Integer.parseInt(args[9]);
	int stelle11 = Integer.parseInt(args[10]);
	int stelle12 = Integer.parseInt(args[11]);
	int stelle13 = Integer.parseInt(args[12]);
	int a        = stelle1*1 + stelle2*3 + stelle3*1 + stelle4*3 + 
                         stelle5*1 + stelle6*3 + stelle7*1 + stelle8*3 + 
                         stelle9*1 + stelle10*3 + stelle11*1 + stelle12*3;
	int b        = 10 - (a % 10);


	System.out.println("Die zu überprüfende ISBN-Nummer lautet:\n" + 
                                  (int)stelle1 +  "" + (int)stelle2 + "" + (int)stelle3 + "-" + 
                                  (int)stelle4 + "-" + (int)stelle5 + "" + (int)stelle6 + ""  +
			          (int)stelle7 + "" + (int)stelle8 + "-"	 + (int)stelle9 + "" + 
                                 (int)stelle10 + "" + (int)stelle11 + "" + (int)stelle12 + "-" + (int)stelle13);

	if (stelle13 == b)    {
	    System.out.println("Die eingegebene ISBN-Nummer ist korrekt");
	}
	else           {
	    System.out.println("Die ISBN-Nummer würde mit korrigierter 
                                     Prüfziffer wie folgt lauten:\n" + (int)stelle1 +  "" + (int)stelle2 + 
                                     "" + (int)stelle3 + "-" + (int)stelle4 + "-" + (int)stelle5 + "" + 
                                    (int)stelle6 + "" + (int)stelle7 + "" + (int)stelle8 + "-" +
			            (int)stelle9 + "" + (int)stelle10 + "" + (int)stelle11 + 
                                    "" + (int)stelle12 + "-" + (int)b);
	}

     }
}
 
Zuletzt bearbeitet:
Ein String ist in anderen Programmiersprachen(z.B. C/Cpp) ein Array von Chars. Java abstrahiert das.
und mit charAt() wird einfach im Char-Array(String) auf Stelle X zugegriffen.

Bei deinem Code liest du die Argumente ein, deren Trennzeichen normalerweise ein Leerzeichen ist.
Du hast als Argumentenliste nämlich, wie du es deklariert hast einen Array von Strings, oder aber einen Array von Array von Chars ;).
Wenn du also nur eine einzige ISBN einlesen willst, so musst du sagen:
PHP:
....
char positionThree = args[0].charAt(2);
....

Cheers

Fluffy
 
heißt das, ich kann nicht mit dem parseInt arbeiten?
also muss ich grundsätzlich meinen code umschreiben oder kann ich trotz der int´s das mit dem charAt seperat für die Eingabe machen?
 
Doch kannst du, aber du musst wissen auf was du hier zugreifst.
Du greifst mittels args[0] nicht auf einzelne Chars zu sondern auf Strings von den Parameterliste die beim Programmaufruf übergeben wurde.
 
Hi,

zuerst einmal solltest du dir den Aufbau einer ISBN-Nummer anschauen und versuchen, diese möglichst standardkonform in deinem Programm abzubilden. Beispielsweise gibt es fünf Vorgaben, wie eine ISBN-Nummer überhaupt auszusehen hat:

1. Präfix, in der Regel 979 oder 978
2. Gruppen-/Ländernummer, eine bis unendlich viele Stellen
3. Verlagsnummer, unendlich viele Stellen
4. Titelnummer, afaik unendlich viele Stellen
5. Prüfziffer, eine Stelle

Im Prinzip hat also jede ISBN die Form aaa-bbb..-ccc..-ddd...-e. Dies kannst du z.B. mit Regular Expressions auch so in deinem Programm abbilden - was aber für den Anfang noch recht komplex ist, weswegen ich es auch erstmal raus lasse. Die Schwäche an deiner Lösung solltest du allerdings bereits erkannt haben.

Übergibst du dem Programm dagegen einen String, so kann dieser potentiell* unendlich lang sein und ist damit zur Abbildung einer ISBN geeignet. Erfreulicherweise bietet Java (im Vergleich zu C) auch einige tolle Funktionen, um einfach und effizient mit Strings arbeiten zu können. Zu nennen sind in diesem Fall z.B. charAt und split. Letzteres ist in deinem Fall besonders nützlich, denn es "spaltet" die Zeichenkette bei einem bestimmten Zeichen auf, z.B. gibt "abc".split("b") das Array ["a","c"] zurück (d.h. durch Split erhälst du ein Array bestehend aus den einzelnen Teilen OHNE das Trennzeichen). Dies kannst du nun ganz einfach auf deine ISBN anwenden und erhälst die einzelnen Teile, die du nun jeweils als eigenständiger Block bearbeiten kannst:

1. array[0] -> Präfix
2. array[1] -> Gruppennummer
3. array[2] -> Verlagsnummer
4. ...

Die einzelnen Teile des Arrays sind wiederum Strings. Um auf die einzelnen Ziffern im String zuzugreifen, kannst du nun z.B. die charAt-Methode nutzen. Somit sollte z.B. array[0].charAt(0) immer den Character '9' zurückgeben. Wenn du diese Ziffer als Integer benötigst, z.B. um die Prüfzahl zu berechnen, darfst du allerdings nicht einfach konvertieren. (int) '5' gibt Beispielsweise 53 zurück, den ASCII/UTF-8/... Dezimalwert für den Char '5'. Du benötigst hierfür die Funktion Character.getNumericValue(char), wie im folgenden Beispiel:

Code:
public class MainTest {
    public static void main(String[] args) {
        char char5 = '5';
        int int5 = (int) char5; // Falsch!
        /*
         * Richtig: int int5 = Character.getNumericValue(char5);
         */
        System.out.println(int5);
    }
}

Der Code wird 53 ausgeben und nicht 5. Die oben einkommentierte Funktion gibt dagegen korrekt 5 aus. Die Funktion Integer.parseInt(char) existiert wider Erwartens nicht.

Die Berechnung der Prüfziffer wird nun natürlich "komplexer", denn nun ist nur zur Laufzeit bekannt, wie lang die einzelnen Teile der ISBN sind. Tipp: Die Methode "abc".length() könnte dir hier weiterhelfen ;)

* Die Begrenzung stellt entweder dein Speicher, oder Integer.MAX_VALUE dar, je nachdem, was kleiner ist. Es ist aber unwahrscheinlich, dass eine ISBN jemals diese Grenze erreichen wird ;)
 
Zuletzt bearbeitet:
Ich kann absolut nachvollziehen, was du sagst und verstehe, wo mein fehler liegt.
Es ist mir leider aber ein komplettes Mysterium, wie ich das jetzt einbauen soll...einfach noch sehr abstrakt alles für mich, auch wenn das sehr einfach sein mag.
Also zuerst brauche ich einen string, den ich beliebig benenne und der muss 17 Stellen haben..und dann definiere ich 17char´s mit charAt() und die Werte dieser char´s als integer bekomme ich mit dem getnumericvalue, damit ich mit den integer´s dann Berechnungen anstellen kann für die Prüfziffer? und die "-" bei der Eingabe kann ich irgendwie mit dem split umgehen ja?
Dann würde das parseInt aber doch wegfallen oder?
Das mit dem abc.length bzw den Sinn darin verstehe ich allerdings noch nicht so ganz, aber das ergibt sich wohl, wenn ich den Anfang ganz durchdrungen habe.
Danke schon mal für die ausführliche Antwort...wirklich toll, dass man so eine Hilfestellung hier kriegt. Umso mehr tut es mir leid, dass ich jetzt nochmal nachfragen muss :/
 
Also zuerst brauche ich einen string, den ich beliebig benenne und der muss 17 Stellen haben..und dann definiere ich 17char´s mit charAt() und die Werte dieser char´s als integer bekomme ich mit dem getnumericvalue, damit ich mit den integer´s dann Berechnungen anstellen kann für die Prüfziffer? und die "-" bei der Eingabe kann ich irgendwie mit dem split umgehen ja?
Das ist richtig. Allerdings musst du von den 17 Stellen abstrahieren (Programmieren bedeutet, dass man von der eigentlichen Aufgabe abstrahiert, sodass man eine generische Lösung erhält, mit der man jede andere Aufgabe der selben "Aufgabenklasse" lösen kann - in deinem Fall könnte die ISBN auch weniger oder mehr als 17 Zeichen haben, dein Programm sollte dann aber immernoch richtig rechnen ;)), d.h. du hast x Stellen, wobei die Zahl x erst zur Laufzeit des Programms bekannt ist. Zum Beispiel liefert folgender Befehl und Code immer die Länge des Strings, den du übergeben hast.

Code:
Code:
public class MainTest {
    public static void main(String[] args) {
        if(args.length!=1) {
            System.out.println("Bitte geben Sie ein Argument ein.");
            System.exit(1);
        }
        int x = args[0].length();
        System.out.println("Ihr Eingabe hat "+x+" Zeichen.");
    }
}

Eingabe:
Code:
Dasisteintest

Ausgabe:
Code:
Ihr Eingabe hat 13 Zeichen.

Nehmen wir an, du hast eine zwei ISBN-Nummern, eine mit 13 Zeichen, eine mit 17 Zeichen. Bei beiden ISBN-Nummern hast du 4 Striche mit drin. Mittels split(..) entfernst du die Zeichen und erhälst nun das im letzten Post genannten Array. Die Länge des ersten Elements aus dem Array muss 3 sein, die des letzten Elements 1, alle anderen können beliebige Länge aufweisen Die Länge der einzelnen Elemente bekommst du bekanntlich wieder mit array[1].length().
Da du nun die Längen der einzelnen Array-Elemente kennst, kannst du mit Hilfe verschiedener Sprachkonstrukte (Verzweigungen, Schleifen, ...) die Prüfsumme berechnen - ohne dir 17 Variablen definieren zu müssen, z.B:

Code:
Code:
public class MainTest {
	public static void main(String[] args) {
		if(args.length<1) {
			System.out.println("Bitte geben Sie mind. ein Argument ein.");
			System.exit(1);
		}
		String[] woerter = args[0].split(" ");
		int anzahlWorter = woerter.length;
		for(int i=0;i<anzahlWorter;i++) {
			int anzahlZeichen = woerter[i].length();
			for(int j=0;j<anzahlZeichen;j++) {
				System.out.println("Buchstabe " + j + " des " + i + "-ten Wortes: "+woerter[i].charAt(j));
			}
		}
	}
}

Eingabe:
Code:
"das ist ein test"

Ausgabe:
Code:
Buchstabe 0 des 0-ten Wortes: d
Buchstabe 1 des 0-ten Wortes: a
Buchstabe 2 des 0-ten Wortes: s
Buchstabe 0 des 1-ten Wortes: i
Buchstabe 1 des 1-ten Wortes: s
Buchstabe 2 des 1-ten Wortes: t
Buchstabe 0 des 2-ten Wortes: e
...


Wichtig: split() ist wieder nur eine Variante neben 100 anderen - wenn du es ohne split machst, sollte das auch passen, z.B.:

Code:
Code:
public class MainTest {
	public static void main(String[] args) {
		if(args.length!=1) {
			System.out.println("Bitte geben Sie ein Argument ein.");
			System.exit(1);
		}
		int x = args[0].length();
		for(int i=0;i<x;i++) {
			System.out.println("Buchstabe "+i+": "+args[0].charAt(i));
		}
	}
}

Eingabe:
Code:
Dasisteintest

Ausgabe:
Code:
Buchstabe 0: D
Buchstabe 1: a
Buchstabe 2: s
Buchstabe 3: i
Buchstabe 4: s
Buchstabe 5: t
Buchstabe 6: e
...

Wie könntest du z.B. alle Buchstaben außer "i" ausgeben?

Dann würde das parseInt aber doch wegfallen oder?
Du musst dir überlegen, welches Ziel du erreichen willst. Dann wählst du deine Methoden aus - und wenn parseInt nicht mehr benötigt wird, dann fällt es eben weg.

Umso mehr tut es mir leid, dass ich jetzt nochmal nachfragen muss :/
Niemand kann "einfach so" Programmieren. Es steckt immer Arbeit dahinter, sich eine Sprache anzueignen, die Grundgedanken dahinter zu verstehen und Abstraktionsvermögen zu entwickeln. Es muss dir nicht leid tun, wenn du nachfragen musst. Im Gegenteil: Wenn du nachfragst merkt dein Gegenüber, dass du dich mit dem Thema aktiv auseinandersetzt - und es dich damit wirklich interessiert! Also wenn du Fragen hast, frag einfach. Es gibt keine dummen Fragen, nur dumme Antworten ;)
 
Zuletzt bearbeitet:
Zurück
Oben