# Logarithmen erstellen mit while-Schleifen



## abc123t (24. Okt 2016)

Hallo!
Ich bin neu hier und programmieren mit Java ist mindestens genau so neu für mich!
"Leider" gehört es zu einem Fach in meinem Studium, eigentlich ist es nicht so schwer, aber die komplexen Matheformeln die wir erstellen müssen, machen mich fertig!

Wir sollen eine Methode "Power" erstellen welche a^b berechnet, a und b geben wir in der Main-Methode ein, und in einer extra Methode sollen wir mit denen rechnen.

ich komme nicht wirklich weiter, da c=a*b; a++; nicht wirklich viel bringt..
Ich stehe wirklich total auf dem Schlau und weiß nicht was ich noch tun soll..

Bis jetzt habe ich:

static int power(int base, int exponent){
        if (base < exponent){
            while (base <= exponent){

                c= base*exponent;
                base++;
            }
        }return base;
    }

Wobei base = a ist und exponent = b. 
Theoretisch bräuchte ich ja noch einen "zwischenspeicher" für c, der dann wiederum wieder ausgetauscht wird, ich habe jedoch keine Ahnung wie ich das umsetzen soll!
Das Paket "Math" dürfen wir nicht benutzen, wir sollen alle Wege selbst implementieren.

Mir würden auch schon Tipps reichen!
Vielen Dank


----------



## Meniskusschaden (24. Okt 2016)

Erst mal solltest du die Berechnung überdenken, denn man potenziert doch nicht, indem man die Basis mit dem Exponenten multipliziert, sondern die Basis mit sich selbst. Der Exponent bestimmt, wie oft das geschehen soll. Den könntest du also jedes Mal um eins verringern und abbrechen, sobald er Null wird.


----------



## Salo (24. Okt 2016)

Und danach könntest du anfangen, deinen code in code-tags zu schreiben.
[ code = java]dein code[/ code]

nur halt ohne leerzeichen, damit es auch wirklich funktioniert.


----------



## JStein52 (25. Okt 2016)

Und falls du deine Power-Methode inzwischen hast ist hier eine optimierte Version:


```
public static long powerRecursive(int base, int exp) {
        if (exp == 0) {
            return 1;
        }
        //braucht noch eine Prüfung auf exp == 1
        if (exp == 1) {
            return base;
        }
        int halfExp = exp / 2;
        int rest = exp % 2;
        long powerOfHalf = powerRecursive(base, halfExp);
        if (rest == 1) {
            return powerOfHalf * powerOfHalf * base;
        } else {
            return powerOfHalf * powerOfHalf;
        }
    }
```


----------



## sascha-sphw (25. Okt 2016)

Und noch eine, wenn wir gerade dabei sind... :-D

```
private static double pow(final double b, double e) {
    if (e > 1) return pow(b, --e) * b;
    else if (e == 0) return 1;
    return b;
}
```


----------



## Xyz1 (25. Okt 2016)

power ist doch 3^4=3*3*3*3 oder? Oder ist etwa Power set damit gemeint??? Das ginge dann nämlich anders.


----------



## InfectedBytes (25. Okt 2016)

Nicht zu empfehlen, aber eine witzige Lösung:

```
public static int pow(int base, int exp) {
    return IntStream.range(0, exp).reduce(1, (a, i) -> a*base);
}
```


----------



## JStein52 (25. Okt 2016)

sascha-sphw hat gesagt.:


> Und noch eine, wenn wir gerade dabei sind...


Die Rekursionstiefe kann problematisch werden. Ich brauche weniger als du


----------



## sascha-sphw (25. Okt 2016)

Genau Werte habe ich auf die schnelle nicht gefunden, aber im Web ist von mehreren tausend Aufrufen die Rede. Wenn man einen größeren Exponenten als 1000 braucht wird es mit Double so und so eng...

```
Double.MAX_VALUE // 1.7976931348623157E308
pow(2, 1000) // 1.0715086071862673E301
```

Die Performance ist da schon eher zu bemängeln.


----------



## JStein52 (26. Okt 2016)

sascha-sphw hat gesagt.:


> pow(2, 1000) // 1.0715086071862673E301


Du weisst dass dies die Anzahl der Atome des Universums sind ? 
Meine Erfahrung mit Rekursion ist dass es bei Rekursionstiefen ab ca. 50 elend langsam wird. Und zwar ziemlich unabhängig von dem eigentlichen Problem das man bearbeitet.


----------



## Xyz1 (26. Okt 2016)

Oder Fakultät 65, ist auch die Anzahl der Atome des Universums.


----------



## stg (27. Okt 2016)

JStein52 hat gesagt.:


> Meine Erfahrung mit Rekursion ist dass es bei Rekursionstiefen ab ca. 50 elend langsam wird. Und zwar ziemlich unabhängig von dem eigentlichen Problem das man bearbeitet.



Was verstehst du unter elend langsam? 19.000 rekursive Aufrufe schaff ich in nicht besonders toller Testumgebung in etwa 1 Millisekunde (dabei wird sogar was "sinnvolles" berechnet). Bei größeren Aufrufzahlen kommts schon zum StackOverflowError.

Bzw. weniger die Tiefe ist das Problem, sondern vielmehr die "Breite" bei schlechten Algorithmen (sagt man das so?  )
Du hast in deinem Beitrag #4 ja gezeigt, wie man rekursiv effizient eine solche Potenz berechnen kann.


----------

