Ancora confronti con il Fortran

Questo post è la continuazione (OK, poi basta) di Un confronto Fortran – Python.


Oggi provo altri due linguaggi. Si comincia con Java, largamente usato, anche se in campi completamente diversi. Una nota per gli eventuali javanisti: ho tentato di tenermi il più fedele possibile alla versione Python; inoltre non uso mai Java e è possibile che ci siano ingenuità e katzate kolossali, benvenute le osservazioni, come al solito.

import static java.lang.Math.pow;
import static java.lang.System.out;

class jconf {
    static double f[];

    public static double fsin(double a) {
        return a - pow(a, 3.0) / f[3] + pow(a, 5.0) / f[5]
                 - pow(a, 7.0) / f[7] + pow(a, 9.0) / f[9]
                 - pow(a, 11.0) / f[11] + pow(a, 13.0) / f[13];
    }

    public static double fcos(double a) {
        return 1.0 - pow(a, 2.0) / f[2] + pow(a, 4.0) / f[4]
                   - pow(a, 6.0) / f[6] + pow(a, 8.0) / f[8]
                   - pow(a, 10.0) / f[10] + pow(a, 12.0) / f[12];
    }

    public static void main(String args[]) {
        int i;
        f = new double[14];
        f[0] = 1.0;
        for (i = 1; i < 14; i++) {
            f[i] = i * f[i - 1];
        }
        int deg = 60 * 60;
        int nsteps = 180 * deg;
        double step = Math.PI / nsteps;
        double ssum = 0.0;
        double csum = 0.0;
        double a, s, c, t = 0.0;

        for (i = 0; i <= nsteps; i++) {
            a = i * step;
            s = fsin(a);
            ssum += s;
            c = fcos(a);
            csum += c;
            if ((i % (10 * deg)) == 0) {
                if (c != 0.0) {
                    t = s / c;
                }
                out.printf("%3d %11.8f %11.8f %11.8f %15.8e\n",
                      (i / deg), a, s, c, t);
            }
        }
        out.println(ssum);
        out.println(csum);
    }

}


Giudizio (provvisorio) di G.: “sembra C“, che sarebbe un grosso difetto.

Poi, solo per confronto, tanto si fa in fretta, ho provato il mio linguaggio di scripting prediletto. Anche qui benvenute le osservazioni ricordando che è la traduzione quasi fedele dello script Python. In effetti mi sono discostato in due punti:

  • per la notazione prefissa del Lisp l’alternanza di somme e sottrazioni nelle funzioni fsin e fcos produrrebbe codice “non bello esteticamente” e allora ho messo il segno nella lista f;
  • sì! l’array f qui è diventato una lista; gli array ci sarebbero anche ma ehi! siamo nel Lisp.
#!/usr/bin/newlisp

;         0 1 2  3  4 5 6  7  8 9 10  11  12 13
(set 'p '(1 1 -1 -1 1 1 -1 -1 1 1 -1  -1  1  1))
(set 'f '(1))
(for (i 1 13)
    (set 't (* (p i) i (abs (f (- i 1)))))
    (push t f i)
)

(define (fsin a)
    (add a (div (pow a 3) (f 3)) (div (pow a 5) (f 5))
           (div (pow a 7) (f 7)) (div (pow a 9) (f 9))
           (div (pow a 11) (f 11)) (div (pow a 13) (f 13))
    )
)

(define (fcos a)
    (add 1 (div (pow a 2) (f 2)) (div (pow a 4) (f 4))
           (div (pow a 6) (f 6)) (div (pow a 8) (f 8))
           (div (pow a 10) (f 10)) (div (pow a 12) (f 12))
    )
)

(set 'pi (mul 4 (atan 1.0))
     'deg (* 60 60)
     'nsteps (* 180 deg)
     'step (div pi nsteps)
)

(set 'ssum 0
     'csum 0
)

(for (i 0 nsteps)
    (set 'a (mul i step)
         's (fsin a)
         'c (fcos a)
    )
    (inc ssum s)
    (inc csum c)
    (if (!= c 0)
        (set 't (div s c)))
    (if (= (mod i (* deg 10)) 0)
        (println (format "%3d %11.8f %11.8f %11.8f %15.8e"
                 (/ i deg) a s c t))
    )
)
(println ssum " " csum)

(exit)


Notare come i due linguaggi di oggi settino il separatore decimale in base alle convenzioni locali; è possibile peraltro ridefinirlo (come anche per il Fortran).

A questo punto riporto, aggiornata, la tabella riassuntiva del confronto. Notate l’ultima riga: il rapporto tra il tempo di esecuzione del linguaggio rispetto a quello del Fortran. Java è in seconda posizione ma lo credevo più performante. Bene newLISP, molto meglio di Python. Naturalmente per quello che questi numeri valgono, la scelta dev’essere fatta rispetto a altre considerazioni, ovviamente.
Poi, OK, non parlo più del Lisp, “dai è peggio del C, se possibile!“, “ma no, dai, vedi com’è bello, uniforme“, ““, ““, ….

Posta un commento o usa questo indirizzo per il trackback.

Commenti

  • glipari  Il 5 luglio 2012 alle 12:34

    No, dai, perché basta? I numeri che hai ottenuto, secondo me, scontano il fatto che tutti i linguaggi che hai provato, tranne il fortran, devono prima caricare l’interprete (o il just-in-time compiler che dir si voglia). Se fai un calcolo più lungo, (che prenda almeno qualche decina di secondi sul fortran), la X/F dovrebb ridursi parecchio.

    E poi, non hai ancora provato il C++ ! 🙂

    • juhan  Il 5 luglio 2012 alle 12:42

      Il C/C++ ha la fama di essere di essere difficile, come Linux e, prima, Unix.
      L’idea di calcolare sin() e cos() per ogni secondo sembrava impegnativa: ai vecchi ricorda il malloppo del Bruhns (chissà se si scrive così?); certo lì c’erano i logaritmi (decimali). Ecco potrebbe essere un’idea per allungare i tempi.
      Mi sa che ci provo, forse, appena ho tempo. Tanto per cambiare sono in ritardo 😦

      • glipari  Il 5 luglio 2012 alle 12:52

        Non mi parlare di ritardo, ormai cronico per me… se non fossi in ritardo, il C++ te lo farei io! (magari stasera che sono solo soletto in quel di Bagneux, e se non crollo dal sonno!)

    • juhan  Il 5 luglio 2012 alle 21:42

      Provato a eseguire 10 cicli di calcolo invece di 1. I rapporti non migliorano, anzi peggiorano leggermente. Domani ci metto i logaritmi (adesso sono troppo cotto) e posto il tutto.
      Intanto una domanda in anticipo: pare che la scelta finale sarà Fortran o Python (probabilmente questo). È sensata? (Poi racconterò perché della scelta).

      • glipari  Il 5 luglio 2012 alle 22:23

        Boh, non saprei dirti. Dipende da: 1) requisiti 2) con quale linguaggio ti trovi meglio. Se I requisiti sono performance, performance e ancora performance, allora fortran. Se sono facilità di programmazione, dinamica, estendiilità, riuso (da parte di qualcun’altro) allora python. Ma questo lo sai già da te! comunque un requisito fondamentale è che chi programma deve conoscere bene il linguaggio, e in questo caso direi che ci siamo!

Trackback

  • […] questa dovrebbe essere l’ultima puntata del tormentone sviluppato negli ultimi post: comincio a detestarlo al pari del caldo afoso che […]

Rispondi

Inserisci i tuoi dati qui sotto o clicca su un'icona per effettuare l'accesso:

Logo di WordPress.com

Stai commentando usando il tuo account WordPress.com. Chiudi sessione /  Modifica )

Google photo

Stai commentando usando il tuo account Google. Chiudi sessione /  Modifica )

Foto Twitter

Stai commentando usando il tuo account Twitter. Chiudi sessione /  Modifica )

Foto di Facebook

Stai commentando usando il tuo account Facebook. Chiudi sessione /  Modifica )

Connessione a %s...

Questo sito utilizza Akismet per ridurre lo spam. Scopri come vengono elaborati i dati derivati dai commenti.

%d blogger hanno fatto clic su Mi Piace per questo: