GRacias chicos, si me interesa. No es un ejercicio de clase, porque como he dicho ya varias veces tengo 14 años.
¿Qué porque quiero hacerlo sin bucle?
Bueno, porque segun mi padre es AVSOLUTAMENTE IMPOSIBLE hacerlo sin bucle y sin funcion pow. ( mi padre no sabe programar pero sabe de lo que hablo porque de pequeño programó en BASIC ). Entonces es exactamente por eso.
El usuario que puso un comentario arriba, no me acuerdo el nombre lo siento, me interesa de lo que hablas...
¿POdrías explicar un poco?
Salu2!
Tampoco hacía falta recordar mi nombre... lo podías copiar y pegar, xD.
A ver, dile a tu padre que sí que se puede hacer sin bucle. Ejemplo;
#include <iostream>
using namespace std;
int pow_aux(int b, int ex) {
if (ex == 0) return 1;
else return b*pow_aux(b,ex-1);
}
double pow(int b, int ex) {
if (ex > 0) return pow_rec(b,ex);
else return 1.0/pow_rec(b,-ex);
}
int main() {
int a,b;
cin >> a >> b;
cout << pow(a,b) << endl;
}
Y bueno, como te han comentado, hace falta tener base matemática para comprender como se haría en el caso del exponente real. Este es mi código:
#include <iostream>
#include <cmath>
#include <vector>
#define GRADMACLAURINSERIES 20
using namespace std;
vector<double> PolyExp;
vector<double> MacLaurinExp(int grad) {
vector<double> Poly(grad+1);
Poly[0] = 1;
for (int i = 1; i <= grad; ++i)
Poly[i] = Poly[i-1]/i;
return Poly;
}
double evalPoly(double x, vector<double> Poly) {
double result = 0;
for (int i = Poly.size()-1; i >= 0; --i)
result = result*x + Poly[i];
return result;
}
double pow_aux(int ex) {
if (ex == 0) return 1;
else return M_E*pow_aux(ex-1);
}
double pow(double b, double ex) {
double result;
ex *= log(b);
if (ex > 0) result = pow_aux(int(ex));
else result = 1.0/pow_aux(int(-ex));
result *= evalPoly(ex-int(ex),PolyExp);
return result;
}
int main() {
double x,y;
PolyExp = MacLaurinExp(GRADMACLAURINSERIES);
cin >> x >> y;
cout.precision(10);
cout << pow(x,y) << endl;
}
MacLaurinExp devuelve los coeficientes de la serie de MacLaurin (polinomio de Taylor en x=0) de la función exponencial (e
x) en un vector. polyEval evalúa el polinomio para un valor de x mediante el algoritmo de Horner.
En mi código, lo que hago básicamente es plantearme una potencia x
y de la siguiente manera: e
ln(x)*y (sólo funciona para bases mayores que 0, claro, para bases menores que 0 el resultado es, en general, complejo, y se tendría que calcular de otra manera). ln(x)*y consta de parte decimal y parte entera. Pongamos que ln(x)*y = 5.64. Como e
5.64=e
5e
0.64la serie de MacLaurin (polinomio de Taylor en x=0) de la función exponencial, lo que hago es evaluar e
5 de la manera tradicional (mediante bucles o mediante una función recursiva, como en este caso con pow_aux) y e
0.64 lo obtengo mediante el polinomio de Taylor de la función exponencial. Luego multiplico los dos resultados y listo, tengo x
y. Insisto en que, para comprender esto, deberías saber lo que es el polinomio de Taylor de una función. Además, considerando que tu nivel de programación todavía no es muy alto, quizás deberías centrarte en seguir aprendiendo antes de preocuparte por estas cosas.
EDITO: Oh, y M_E es una macro definida en cmath, que contiene el número e con la máxima precisión que admite la máquina.
Saludos
EI: juntando mensajes.Ah, aquí una implementación mucho más eficiente del algoritmo para exponentes enteros. Si bien en los algoritmos dados hasta ahora el coste era Θ(n), en éste el coste es Θ(log n), lo cual es una mejora MUY importante.
#include <iostream>
using namespace std;
double pow_aux(double b, int e) {
if (e == 0) return 1;
else {
double x = pow_aux(b, e/2);
if (e%2) return x*x*b;
else return x*x;
}
}
double pow(double b, int e) {
if (e < 0) return 1/pow_aux(b,-e);
else return pow_aux(b,e);
}
int main() {
double b;
int e;
cin >> b >> e;
cout << pow(b,e) << endl;
}