IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

JavaScript Discussion :

Rigueur mathématique, une idée ?


Sujet :

JavaScript

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Membre expérimenté
    Profil pro
    Inscrit en
    Mars 2006
    Messages
    319
    Détails du profil
    Informations personnelles :
    Âge : 44
    Localisation : Belgique

    Informations forums :
    Inscription : Mars 2006
    Messages : 319
    Par défaut Rigueur mathématique, une idée ?
    Salut !

    Je n'avais jamais vraiment réalisé à quel point la précision des nombres en JavaScript était... étrange. Il parait qu'ils sont codés / stockés sur 64 bits, ce qui devrait nous donner une certaine précision dans leur manipulation, alors j'imaginais que, par exemple 0.01 + 0.06 donnerait 0.07. Mais... non ! Bref, je vous laisse faire le test pour connaître ce résultat merveilleux.

    Passons aux choses sérieuses. En dessous je vous glisse le code d'une petite classe utilitaire. Avec, vous pourrez essayer l'instruction suivante, qui donne un résultat fort intéressant aussi.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    with(Coordinates) {
        convert(convert([1,1], SPHERICAL), SPHERICAL, CARTESIAN);
    }
    On pourrait s'attendre à retrouver [1, 1] mais... que neni !

    Si d'aventure un expert des chiffres venait à passer par là, ou n'importe qui ayant une idée pertinente en fait...

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    Coordinates = {
        CARTESIAN: 0x01,
        SPHERICAL: 0x02,
     
        /** Converts some coordinates from one system to another. */
        convert: function(coordinates, context, target) {
            // Only the target might be defined. In that case, it is passed as the first parameter.
            if(!target) {
                if(!context) {
                    throw new Error("Targeted space required.");
                }
                target = context;
                context = Coordinates.CARTESIAN;
            }
     
            var result = null;
     
            if(target != context) {
                // Working with 3 dimensions.
                while(coordinates.length < 3) {
                    coordinates.push(0);
                }
     
                switch(context) {
                    case Coordinates.CARTESIAN:
                        switch(target) {
                            case Coordinates.SPHERICAL:
                                with(Math) {
                                    var x = coordinates[0];
                                    var y = coordinates[1];
                                    var z = coordinates[2];
                                    var rho = sqrt(pow(x, 2) + pow(y, 2) + pow(z, 2));
                                    var phi = acos(z / rho) || 0;
                                    var theta = acos(x / sqrt(pow(x, 2) + pow(y, 2))) || 0;
                                    if(y < 0) {
                                        theta = 2 * PI - theta;
                                    }
     
                                    result = [rho, phi, theta];
                                }
                                break;
                        }
                        break;
                    case Coordinates.SPHERICAL:
                        switch(target) {
                            case Coordinates.CARTESIAN:
                                with(Math) {
                                    var rho = coordinates[0];
                                    var phi = coordinates[1];
                                    var theta = coordinates[2];
                                    var x = rho * sin(phi) * cos(theta);
                                    var y = rho * sin(phi) * sin(theta);
                                    var z = rho * cos(phi);
     
                                    result = [x, y, z];
                                }
                                break;
                        }
                        break;
                }
            }
            else {
                throw new Error(&quot;Conversion is to be made between two diferent spaces.&quot;);
            }
     
            return result;
        }
    }

  2. #2
    jnore
    Invité(e)
    Par défaut
    Bonsoir,

    Je ne suis pas un spécialiste des nombres, j'avoue que le résultat est étonnant!

    Pour ce qui est du premier problème, lorsque l'on utilise la méthode suivante, la précision revient.
    Code javascript : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
     
    var a=0.01;
    var b=0.06;
    var c=a+b;
    alert(c.toPrecision(15));

  3. #3
    Membre chevronné
    Profil pro
    Inscrit en
    Juin 2009
    Messages
    313
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2009
    Messages : 313
    Par défaut
    Le problème est ailleurs :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
     
    var rho = sqrt(x * x + y * y + z * z);
    var phi = asin(z / rho) || 0;
    var theta = atan2(y,x) || 0;
    et :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
     
    var x = rho * cos(phi) * cos(theta);
    var y = rho * cos(phi) * sin(theta);
    var z = rho * sin(phi);

  4. #4
    Membre expérimenté
    Profil pro
    Inscrit en
    Mars 2006
    Messages
    319
    Détails du profil
    Informations personnelles :
    Âge : 44
    Localisation : Belgique

    Informations forums :
    Inscription : Mars 2006
    Messages : 319
    Par défaut
    Excellent jnore, merci !

    kernelfailure, d'où viennent tes formules ? J'ai pris les miennes sur Wikipédia. Avec les tiennes on obtient : [1.0000000000000002, 1, 0] au lieu de
    [1, 1.0000000000000002, 8.659560562354934e-17]. Dans les deux cas demeure le problème d'imprécision. Je pense que je vais utiliser "toPrecision" pour palier à ça mais je suis curieux de savoir sur quoi se basent tes formules. Dans l'article Wikipédia sus-cité phi est l'angle formé entre z¯ et OP¯, et thêta celui formé entre et OH¯, H étant le projeté de P dans le plan xy.

    Merci à vous deux !

  5. #5
    Membre chevronné
    Profil pro
    Inscrit en
    Juin 2009
    Messages
    313
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2009
    Messages : 313
    Par défaut
    Désolé pour le retard

    J'ai récupéré ça, quelque part sur le net. Ce qui me gênait dans ta formule, c'était le redressement conditionné.

    J'avais souvenir de méthodes plus "directes" et d'un sinus pour changer en coordonnée cartésienne sur z, alors j'ai cherché.

Discussions similaires

  1. Une idée pour un débutant
    Par poutine dans le forum C
    Réponses: 15
    Dernier message: 04/05/2006, 21h54
  2. [Listes ou Chaines de caractères] Une idée..
    Par KiLVaiDeN dans le forum Algorithmes et structures de données
    Réponses: 3
    Dernier message: 25/04/2006, 11h54
  3. Une idée pour utiliser ce type de fichier data??
    Par Frenchy dans le forum DirectX
    Réponses: 2
    Dernier message: 14/02/2006, 13h24
  4. Relation de dépendance entre résultats : une idée farfelue ?
    Par mdef dans le forum Langages de programmation
    Réponses: 4
    Dernier message: 18/07/2005, 02h04

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo