es wird falsch gekürzt

Status
Nicht offen für weitere Antworten.

maeck

Mitglied
Hi,

ich bin noch recht neu in Java und bekomm ein Kürzungsproblem nicht auf die Reihe.
Habe folgenden Code:
Code:
public Rational(long numerator, long denominator) {
    	if (denominator == 0)
    			throw new ArithmeticException("Nenner darf nicht 0 sein!");
        long g = gcd(numerator, denominator);
        numerator /=g ;
        denominator /= g;
        this.zaehler = numerator;
        this.nenner = denominator;
    }
    
    private static long gcd(long a, long b) {
        while (b != 0) {
            long t = a % b;
            a = b;
            b = t;	
        	
        }
        return a;
    }
Wenn ich z.B. -100, 24 übergebe, dann sollten -25, 6 rauskommen. Es kommen aber 25,-6 raus.
Vielleicht häng ich auch schon zu lange dran, aber ich seh den Fehler leider nicht.
 
Ich hab's jetzt nicht nachgeprüft, aber vielleicht liegt's ja an der
Verbindung des Modulo-Operators mit negativen Zahlen?

Rechne in deiner gcd-Methode doch mal mit den Absolutwerten. ???:L
 
Meines Wissens sollte Modulo mit negativen Zahlen klar kommen 🙁
Was meinst du mit Absolutwerten? Konkrete Zahlen?
 
schau dir doch deien gcd-Algorithmus an oder benutze lauter System.out.println um zu sehen, was dort passiert,

da wird a und b munter vertauscht, ohne dass auf das Vorzeichen geachtet wird,
am Ende kommt da zufällig 4 oder -4 raus,
spielt im Algorithmus keine Rolle,

du solltest also vor den endgültigen return das evtl. vorhande Negationszeichen entfernen:
return Math.abs(a);
oder so
 
Ja aber wenn ich das Vorzeichen entferne, dann funktioniert es auch nicht richtig.

Habe mir folgende Testdaten geschrieben:
Rational r = new Rational(100, 24);
assertEquals(25, r.numerator());
assertEquals(6, r.denominator());

r = new Rational(-100, -24);
assertEquals(25, r.numerator());
assertEquals(6, r.denominator());

r = new Rational(-100, 24);
assertEquals(-25, r.numerator());
assertEquals(6, r.denominator());

r = new Rational(100, -24);
assertEquals(-25, r.numerator());
assertEquals(6, r.denominator());

Wenn ich abs benutze, dann klappen die ersten beiden nicht, und wenn ich abs weg lasse, dann die letzten beiden nicht.

Also muss ich es noch anders lösen 🙁
 
na das sind ja merkwürdige Bedingungen,
so gehts für diese vier Fälle
(Regel: wenn zweite Zahl negativ, dann gcd negativ machen):

Code:
public class Rational {

    public Rational() {
        doSomething(100, 24);
        doSomething(-100, -24);
        doSomething(-100, 24);
        doSomething(100, -24);
    }

    public void doSomething(long numerator, long denominator) {
        if (denominator == 0)
            throw new ArithmeticException("Nenner darf nicht 0 sein!");
        long g = gcd(numerator, denominator);
        long numerator2 = numerator / g;
        long denominator2 = denominator / g;
        System.out.println("num: " + numerator + " den: " + denominator + " --> g: " + g + 
                " num2: " + numerator2 + " den2: " + denominator2);
    }

    private static long gcd(long a, long b) {
        boolean negative = ( b < 0 );
        while (b != 0) {
            long t = a % b;
            a = b;
            b = t;

        }
        a = Math.abs(a);
        if (negative) {
            return -a;
        } else {
            return a;
        }
    }

    public static void main(String[] args) {
        new Rational();
    }

}
 
Status
Nicht offen für weitere Antworten.

Neue Themen


Zurück
Oben