Trigo et degrés

Vous avez une idée pour améliorer ou modifier PureBasic ? N'hésitez pas à la proposer.
Avatar de l’utilisateur
cederavic
Messages : 1338
Inscription : lun. 09/févr./2004 23:38
Localisation : Bordeaux

Message par cederavic »

un bout de code ça parle toujours mieu :

Code : Tout sélectionner


For h = 0 To 4
  Delay(1000)
  
  ti = ElapsedMilliseconds()
  For t= 0 To 1000000
    ac = Cos(Random(314) / 100)
  Next
  ta = ElapsedMilliseconds() - ti
  Debug "Normal : " + Str(ta)
  
  Delay(1000)
  
  ti = ElapsedMilliseconds()
  For t= 0 To 1000000
    ac = Cos(Random(314) / 100 * 1);1 car #PB_Math_Rad serait = 1 si on serait en radian par defaut
  Next
  ta = ElapsedMilliseconds() - ti
  Debug "Ced : " + Str(ta)
  
  
  m = 2 ; imaginons que le Mode radian = 2
  Delay(1000)
  
  ti = ElapsedMilliseconds()
  For t= 0 To 1000000
    If m = 2
      ac = Cos(Random(314) / 100)
    EndIf
  Next
  ta = ElapsedMilliseconds() - ti
  Debug "Dri : " + Str(ta)
Next
Dr. Dri
Messages : 2527
Inscription : ven. 23/janv./2004 18:10

Message par Dr. Dri »

Bon puisqu'il faut entrer dans les tests de performances alors pourquoi pas...
Première chose, on ne fait pas de test de vitesse avec le debugger
Deuxième chose, on ne compare pas des fonctions persos avec des fonctions natives. Les fonctions persos contiennent des entêtes qui prennent un petit temps CPU non négligeable comme le montre cet exemple:

Code : Tout sélectionner

Procedure.f Cos_(Angle.f)
  !FLD  dword [esp]
  !FCOS
EndProcedure

cos.f
Angle.f = Random(123)

;test avec la version native

depart = ElapsedMilliseconds()

For t= 0 To 1000000
  cos = Cos( Angle )
Next

duree = ElapsedMilliseconds() - depart

MessageRequester(StrF(cos), Str(duree))

;test avec la version perso

depart = ElapsedMilliseconds()

For t= 0 To 1000000
  cos = Cos_( Angle )
Next

duree = ElapsedMilliseconds() - depart

MessageRequester(StrF(cos), Str(duree))
Donc pour pouvoir comparer des choses comparables on va commencer par ne pas utiliser la fonction native de PB car si le systeme que je propose était natif il bénéficierai des mêmes augmentations de vitesse puisque les entetes disparaitrait. C'est pourquoi on va se baser une fonction RealCos comme dans l'exemple de cederavic.

Maintenant on fait les tests avec la fonction proposée et aussi avec la version native (remplacée pour les raisons qui précèdent) dans l'exemple que voici:
(ne pas oublier de noter le résultat, en moyenne 125 et 123 pour moi)

Code : Tout sélectionner

;la version proposée (simplifiée)
Enumeration
  #PB_Math_Rad
  #PB_Math_Deg
  #PB_Math_Grd
EndEnumeration

Global Pi.f ;la pseudo constante...
Pi = ValF("3.14159274101257320")

Global _PB_Math_Angles.l, _PB_Math_Coeff.f
_PB_Math_Angles = #PB_Math_Deg  ;je garde l'idée des degrés par défaut
_PB_Math_Coeff  = _PB_Coeff_Deg ;même si c'est pas le plus important

Procedure.l SetMathAngles(Type.l)
  Protected Error.l
 
  Select Type
    Case #PB_Math_Rad
      _PB_Math_Coeff = 1.0
    Case #PB_Math_Deg
      _PB_Math_Coeff = Pi / 180
    Case #PB_Math_Grd
      _PB_Math_Coeff = Pi / 200
    Default
      Error = #True
  EndSelect
 
  If Error = #False
    _PB_Math_Angles = Type
  EndIf
 
  ProcedureReturn Error ! #True
EndProcedure

Procedure.f Cos_(Angle.f)
  If _PB_Math_Angles
    Angle * _PB_Math_Coeff
  EndIf
  
  !FLD  dword [esp]
  !FCOS
EndProcedure

;le test
SetMathAngles(#PB_Math_Rad)

cos.f
Angle.f = Pi

depart = ElapsedMilliseconds()

For t= 0 To 1000000
  cos = Cos_( Angle )
Next

duree = ElapsedMilliseconds() - depart

MessageRequester(StrF(cos), Str(duree))

;le remplacement de la fonction native
Procedure.f RealCos(Angle.f)
  !FLD  dword [esp]
  !FCOS
EndProcedure

;le test

cos.f
Angle.f = Pi

depart = ElapsedMilliseconds()

For t= 0 To 1000000
  cos = RealCos( Angle )
Next

duree = ElapsedMilliseconds() - depart

MessageRequester(StrF(cos), Str(duree))
Voila, je pense que mon teste est un tantinet plus pertinent, et assez révélateur par la même occasion. Maintenant si y'en a qui trouvent encore à redire là dessus je crois que j'ai plus d'arguments cachés dans mes manches.

Dri :roll:
Avatar de l’utilisateur
cederavic
Messages : 1338
Inscription : lun. 09/févr./2004 23:38
Localisation : Bordeaux

Message par cederavic »

Un peut byzard ton test, j'ai un meilleur resultat avec Cos_() qu'avec RealCos(). Et la je pense que c'est toi qui ne veux rien savoir, car aparement tu n'a pas remarquer que ma methode n'est ni plus ni moin que la tienne sans If. Deplus dans mon test, ma methode et ta methode sont bien comparable car soumises au meme contraintes (ce qui n'est pas le cas avec le fonction native je suis d'accord).
Dr. Dri
Messages : 2527
Inscription : ven. 23/janv./2004 18:10

Message par Dr. Dri »

En fait j'ai pas vraiment compris, donc si tu pouvais m'expliquer plus en détails

Dri :oops:
Avatar de l’utilisateur
cederavic
Messages : 1338
Inscription : lun. 09/févr./2004 23:38
Localisation : Bordeaux

Message par cederavic »

Dr. Dri a écrit :En fait j'ai pas vraiment compris, donc si tu pouvais m'expliquer plus en détails

Dri :oops:
Au lieu d'avoir un SetMathAngles() et donc des IF, on donne le coef directement avec un param optionnel. Par exemple : Cos(Angle, #PB_Math_Deg) où #PB_Math_Deg = 180 / Pi
Cos vu de l'interieur ressemblerai ici à Cos(Angle * 180 / Pi)
Dr. Dri
Messages : 2527
Inscription : ven. 23/janv./2004 18:10

Message par Dr. Dri »

cederavic a écrit :Au lieu d'avoir un SetMathAngles() et donc des IF, on donne le coef directement avec un param optionnel. Par exemple : Cos(Angle, #PB_Math_Deg) où #PB_Math_Deg = 180 / Pi
Cos vu de l'interieur ressemblerai ici à Cos(Angle * 180 / Pi)
C'est bien ce que j'ai cru comprendre, le truc c'est que ca encombre le code
Autant directement faire Cos(Angle * 180 / Pi)

C'est pour cette raison que je propose tout mon bazar ^^
Tu choisis les angles et hop t'as plus de souci avec les conversions
Du coup t'utilises les fonctions comme si de rien n'était

Dri :)
lionel_om
Messages : 1500
Inscription : jeu. 25/mars/2004 11:23
Localisation : Sophia Antipolis (Nice)
Contact :

Message par lionel_om »

Moi je suis d'accord avec Dr. Dri. C'ets une bonne idée de faire un truc auto comme il le propose. Car y'en a pleins qui clamment que le radian c'est indispensable en native, mais :
1) il ne le réfute pas, mais veut simplement plus de souplesse pour ceux qui ne veulent pas se prendre la tête, sans déranger les "bêtes en maths"...
2) y'en a qui se disent partir du forum si [...], mais qui (il me semble) n'ont jamais pondu un code sur les maths. Dri et Comptois sont les seuls (sur le forum français) à poster des codes avec de la trigo. Donc je trouve un peu gonflé de se la raconter en disant : "moi j'suis un dieu en maths et toi t'es de la merde" et n'avoir jamais rien posté (donc pe etre jamais rien fait), surtout qu'encore une fois pour les "matheux", dc pas très "littéraires" qu'il ne poste pas cela pour vous emmerder et ralentir vos chers petits Cos, mais juste pour alléger les codes...
Webmestre de Basic-univers
Participez à son extension: ajouter vos programmes et partagez vos codes !
Avatar de l’utilisateur
djes
Messages : 4252
Inscription : ven. 11/févr./2005 17:34
Localisation : Arras, France

Message par djes »

Vous auriez dû rajouter qu'il y en a qui veulent bien des degrés si ça ne ralentit pas (DU TOUT) les radians.

Pourquoi j'insiste là dessus? Parce que les fonctions trigos sont les plus utilisées dans les calculs intensifs en 3D. Comme il n'est pas rare d'avoir plusieurs milliers de points à calculer en 3D, le plus petit cycle perdu est dommageable. Donc, il faut éviter les tests et autres horreurs dans ce genre.

Au début, Dri était pour l'utilisation d'un subsystem, ce qui me semble idéal, car dans ce cas, il n'y a pas de perte de vitesse : grâce à une constante définie dans le code, le compilateur prend des fonctions (natives) en degrés ou en radians (c'est quand même à vérifier, je n'en suis pas sûr à 100%). Par contre, je ne sais pas si on pourrait changer de système plusieurs fois, il faudrait donc quand même des fonctions de conversions.

Si maintenant on fait des IF ou autres tests, on y perd en vitesse et je suis contre.
Dr. Dri
Messages : 2527
Inscription : ven. 23/janv./2004 18:10

Message par Dr. Dri »

djes a écrit :Si maintenant on fait des IF ou autres tests, on y perd en vitesse et je suis contre.
Si tu as un réel besoin de vitesse, calcule ton cosinus directement en assembleur, pas d'utilisation de la pile, là t'as aucune perte... Surtout qu'en PB c'est pas difficile...

Dri
Guimauve
Messages : 1015
Inscription : mer. 11/févr./2004 0:32
Localisation : Québec, Canada

Message par Guimauve »

Message supprimé
Dernière modification par Guimauve le sam. 11/févr./2006 2:36, modifié 2 fois.
lionel_om
Messages : 1500
Inscription : jeu. 25/mars/2004 11:23
Localisation : Sophia Antipolis (Nice)
Contact :

Message par lionel_om »

Moi j'ai :
La fonction RealCos() avec 3.141592/3 = 0.500000
La fonction Cos() de PB avec 3.141592/3 = 0.500000
La fonction RealCos() avec0 = 1.000000
La fonction RealCos() avec1 = 0.540302
La fonction RealCos() avec2 = -0.416147
La fonction RealCos() avec3 = -0.989992
La fonction RealCos() avec4 = -0.653644
La fonction RealCos() avec5 = 0.283662
Donc ca marche :wink: (v3.9x)

Par contre sur la v4, ca donne bien 1.000000 partout...
Bug de la v4 ???
Webmestre de Basic-univers
Participez à son extension: ajouter vos programmes et partagez vos codes !
Backup
Messages : 14526
Inscription : lun. 26/avr./2004 0:40

Message par Backup »

....
Dernière modification par Backup le mar. 19/août/2014 15:33, modifié 1 fois.
Avatar de l’utilisateur
djes
Messages : 4252
Inscription : ven. 11/févr./2005 17:34
Localisation : Arras, France

Message par djes »

Dr. Dri a écrit :
djes a écrit :Si maintenant on fait des IF ou autres tests, on y perd en vitesse et je suis contre.
Si tu as un réel besoin de vitesse, calcule ton cosinus directement en assembleur, pas d'utilisation de la pile, là t'as aucune perte... Surtout qu'en PB c'est pas difficile...

Dri
Oui, quelque part t'as raison... Et quelque part t'as tort aussi puisque j'aime PB parce qu'il est à mi-chemin entre convivialité et rapidité... Si je voulais la simplicité je prendrais VB :twisted: Si je voulais la rapidité pure, je ferais tout en assembleur!

Bref, on n'en sort pas! :lol:
J'abandonne!
Frenchy Pilou
Messages : 2194
Inscription : jeu. 27/janv./2005 19:07

Message par Frenchy Pilou »

@Dobro
En plus si tu mets une photo à la place du texte cela ferait une horloge originale :lol:
Et si .... sonnait, on aurait l'heure :lol: (célèbre contine)
Excusez-moi, j'ai pas pu résisté, c'était l'occasion rêvée :roll:
Dernière modification par Frenchy Pilou le jeu. 09/févr./2006 1:54, modifié 1 fois.
Est beau ce qui plaît sans concept :)
Speedy Galerie
Avatar de l’utilisateur
djes
Messages : 4252
Inscription : ven. 11/févr./2005 17:34
Localisation : Arras, France

Message par djes »

Dobro a écrit :moi aussi la preuve voici ce que je montre a ceux qui ne veulent pas des
degres
C'est pas un site de c** ici! :D
Répondre