author | Alberto Bertogli
<albertito@blitiri.com.ar> 2010-09-07 00:29:44 UTC |
committer | Alberto Bertogli
<albertito@blitiri.com.ar> 2010-09-07 01:28:24 UTC |
parent | e4926de3f18309aa13d40c267998582939bcc071 |
.gitignore | +3 | -0 |
Makefile | +16 | -0 |
binomial.cpp | +3 | -2 |
binomial_inc.cpp | +3 | -2 |
err.py | +30 | -0 |
gen_plot_data.sh | +74 | -0 |
plot.gpi | +94 | -0 |
diff --git a/.gitignore b/.gitignore index 332b482..bc38cef 100644 --- a/.gitignore +++ b/.gitignore @@ -8,3 +8,6 @@ binomial_dec fcont fcont_int +out/ +plot/ + diff --git a/Makefile b/Makefile index 312759d..eafd74f 100644 --- a/Makefile +++ b/Makefile @@ -27,6 +27,7 @@ binomial_inc: $(OBJS) binomial_inc.o binomial_dec: $(OBJS) binomial_dec.o $(CXX) $(CXXFLAGS) $^ -o $@ + clean: rm -f $(OBJS) rm -f calc.o calc @@ -37,3 +38,18 @@ clean: rm -f binomial_inc binomial_inc.o rm -f binomial_dec binomial_dec.o +plot_data: out/plot_data + +out/plot_data: all + mkdir -p out + ./gen_plot_data.sh + touch out/plot_data + +plot: plot_data plot.gpi + mkdir -p plot/ + gnuplot plot.gpi + +clean_plot: + rm -rf out/ + rm -rf plot/ + diff --git a/binomial.cpp b/binomial.cpp index 18c6efd..24611c4 100644 --- a/binomial.cpp +++ b/binomial.cpp @@ -55,9 +55,10 @@ int main(int argc, char *argv[]) printf(" ---\n"); #endif //printf(" %d %.60f 0x%" print_64t "x\n", i, n.to_double(), to_u64(n)); - } - print_result(nterm, n); + /* Vamos emitiendo los resultados a medida que los tenemos */ + print_result(i, n); + } return 0; } diff --git a/binomial_inc.cpp b/binomial_inc.cpp index a350eb6..39587e5 100644 --- a/binomial_inc.cpp +++ b/binomial_inc.cpp @@ -64,9 +64,10 @@ int main(int argc, char *argv[]) printf(" ---\n"); #endif //printf(" %d %.60f 0x%" print_64t "x\n", i, n.to_double(), to_u64(n)); - } - print_result(nterm, n); + /* Vamos emitiendo los resultados a medida que los tenemos */ + print_result(i + 1, n); + } return 0; } diff --git a/err.py b/err.py new file mode 100755 index 0000000..e80ae18 --- /dev/null +++ b/err.py @@ -0,0 +1,30 @@ +#!/usr/bin/env python + +""" +Esta utilidad recibe la salida de los distintos algoritmos (que esta siempre +en el mismo formato), y la emite tal cual, pero agregando al final de cada +linea el error del resultado, comparandolo con uno conocido y utilizando +aritmetica de precision fija a 90 digitos. +""" + +import sys +from decimal import Decimal, getcontext + +# Precision de los decimales a 90 digitos +getcontext().prec = 90 + +# Cargamos la posta, tiene 98 digitos +P = Decimal('1.41421356237309504880168872420969807856967187537694807317667973799073247846210703885038753432764157') + +# Procesamos la entrada +for l in sys.stdin.readlines(): + niters, prec, resultado, res_hex = l.split() + + # Calculamos el error, escalado en 100 millones para graficarlo mejor + # ya que gnuplot usa doubles + r = Decimal(resultado) + error = abs(P - r) * 100 * 1000000 + + print l.strip(), error + + diff --git a/gen_plot_data.sh b/gen_plot_data.sh new file mode 100755 index 0000000..10a3c86 --- /dev/null +++ b/gen_plot_data.sh @@ -0,0 +1,74 @@ +#!/bin/bash + +# Directorio de salida, coordinado con el graficador +OUTDIR="out/" +mkdir -p $OUTDIR + +# Minima y maxima precision a calcular +minprec=10 +maxprec=51 + +# Tabla con los algoritmos a usar, y la cantidad minima y maxima de +# iteraciones para el mismo +declare -A maxiter +declare -A miniter +miniter["babilonio"]=1 +maxiter["babilonio"]=50 +miniter["binomial"]=1 +maxiter["binomial"]=300 +miniter["binomial_inc"]=1 +maxiter["binomial_inc"]=300 +miniter["binomial_dec"]=10 +maxiter["binomial_dec"]=300 +miniter["fcont"]=1 +maxiter["fcont"]=50 +miniter["fcont_int"]=1 +maxiter["fcont_int"]=50 + +# Algunos algoritmos son incrementales, y nos dan los resultados en cada +# iteración hasta que llegan a la indicada en la linea de comandos, para +# optimizar las corridas. Estos estan indicados en este arreglo. +declare -A isincr +isincr["binomial"]=1 +isincr["binomial_inc"]=1 + +algolist=${!maxiter[*]} + + +# Corremos y guardamos en archivos por algoritmo y por precision +for algo in $algolist; do + echo -n "$algo " >&2 + for prec in `seq $minprec $maxprec`; do + echo -n "$prec " >&2 + OF="$OUTDIR/OUT-$algo-prec:$prec" + rm -f "$OF" + + # Si no es incremental, entonces hacemos nosotros a mano el + # loop para cada iteración; sino directamente corremos el + # programa con la máxima iteración buscada + if [ "${isincr[$algo]}" == "" ]; then + for iter in `seq ${miniter[$algo]} ${maxiter[$algo]}`; do + ./$algo $prec $iter >> "$OF" + done + else + ./$algo $prec ${maxiter[$algo]} > "$OF" + fi + + # Obtenemos los errores de cada resultado + cat "$OF" | ./err.py > "$OF-err" + done + echo >&2 +done + + +# Obtenemos archivos por iteracion, asegurandonos que esten bien ordenados +# para no confundir al graficador +echo "iter split" +for algo in $algolist; do + for iter in `seq 1 ${maxiter[$algo]}`; do + cat "$OUTDIR"/OUT-$algo-prec:*-err | egrep "^$iter" \ + | sort -n -k 2 \ + > "$OUTDIR/OUT-$algo-iter:$iter-err" + done +done + diff --git a/plot.gpi b/plot.gpi new file mode 100644 index 0000000..1f2e43e --- /dev/null +++ b/plot.gpi @@ -0,0 +1,94 @@ + +set terminal png enhanced size 1024,768 +set autoscale +set style data linespoints + +# +# Error con precision fija e iteración variable +# + +set ylabel "Error * 100 millones" + +set xlabel "Iteración" + +# Babilonio +set output "plot/babilonio-err-p:51.png" +set title "Babilonio con precisión 51 - Error" +plot \ + 'out/OUT-babilonio-prec:51-err' using 1:5 title "Babilonio" + +set output "plot/babilonio-err-p:51-detalle.png" +set title "Babilonio con precisión 51 - Error - Detalle" +plot [2:10] \ + 'out/OUT-babilonio-prec:51-err' using 1:5 title "Babilonio" + +# Binomial +set output "plot/binomial-err-p:51.png" +set title "Binomial con precisión 51 - Error" +plot \ + 'out/OUT-binomial-prec:51-err' using 1:5 title "Binomial", \ + 'out/OUT-binomial_inc-prec:51-err' using 1:5 title "Binomial inc", \ + 'out/OUT-binomial_dec-prec:51-err' using 1:5 title "Binomial dec" + +set output "plot/binomial-err-p:51-detalle.png" +set title "Binomial con precisión 51 - Error - Detalle" +plot [25:] \ + 'out/OUT-binomial-prec:51-err' using 1:5 title "Binomial", \ + 'out/OUT-binomial_inc-prec:51-err' using 1:5 title "Binomial inc", \ + 'out/OUT-binomial_dec-prec:51-err' using 1:5 title "Binomial dec" + +# Fracciones continuas +set output "plot/fcont-err-p:51.png" +set title "Fracciones continuas con precisión 51 - Error" +plot \ + 'out/OUT-fcont-prec:51-err' using 1:5 title "Frac. continuas", \ + 'out/OUT-fcont_int-prec:51-err' using 1:5 title "Frac. continuas int" + +set output "plot/fcont-err-p:51-detalle.png" +set title "Fracciones continuas con precisión 51 - Error - Detalle" +plot [3:10] \ + 'out/OUT-fcont-prec:51-err' using 1:5 title "Frac. continuas", \ + 'out/OUT-fcont_int-prec:51-err' using 1:5 title "Frac. continuas int" + + +# Comparativas +set output "plot/todos-err-p:51-detalle.png" +set title "Comparativa con precisión 51 - Error - Detalle" +plot [25:] \ + 'out/OUT-fcont-prec:51-err' using 1:5 title "Frac. continuas", \ + 'out/OUT-fcont_int-prec:51-err' using 1:5 title "Frac. continuas int", \ + 'out/OUT-binomial-prec:51-err' using 1:5 title "Binomial", \ + 'out/OUT-binomial_inc-prec:51-err' using 1:5 title "Binomial inc", \ + 'out/OUT-binomial_dec-prec:51-err' using 1:5 title "Binomial dec", \ + 'out/OUT-babilonio-prec:51-err' using 1:5 title "Babilonio" + + +# +# Error con precision variable e iteración fija +# + +set xlabel "Precisión (dígitos)" + +# Babilonio +set output "plot/babilonio-err-i:50.png" +set title "Babilonio en iteración 50 - Error" +plot \ + 'out/OUT-babilonio-iter:50-err' using 2:5 title "Babilonio" + +# Binomial +set output "plot/binomial-err-i:100.png" +set title "Binomial en iteración 100 - Error" +plot \ + 'out/OUT-binomial-iter:100-err' using 2:5 title "Binomial", \ + 'out/OUT-binomial_inc-iter:100-err' using 2:5 title "Binomial inc", \ + 'out/OUT-binomial_dec-iter:100-err' using 2:5 title "Binomial dec" + +# Fracciones continuas +set output "plot/fcont-err-i:10.png" +set title "Fracciones continuas en iteración 10 - Error" +plot \ + 'out/OUT-fcont-iter:10-err' using 2:5 title "Frac. continuas", \ + 'out/OUT-fcont_int-iter:10-err' using 2:5 title "Frac. continuas int" + +# Comparativas +