Flotteur vs Double Performance

J’ai fait des tests de timing et j’ai lu des articles comme celui-ci (dernier commentaire), et il semble que dans la version Release, les valeurs flottantes et doubles prennent le même temps de traitement.

Comment est-ce possible? Lorsque float est moins précis et plus petit que les valeurs doubles, comment le CLR peut-il doubler le temps de traitement?

Sur les processeurs x86, au moins, float et double seront chacun convertis en un réel de 10 octets par la FPU pour traitement. La FPU ne dispose pas d’unités de traitement distinctes pour les différents types de virgule flottante qu’elle prend en charge.

L’ancien conseil que float est plus rapide que le double appliqué il y a 100 ans lorsque la plupart des processeurs n’avaient pas de FPU intégrés (et peu de gens avaient des puces FPU séparées), la plupart des manipulations en virgule flottante se faisant dans le logiciel. Sur ces machines (alimentées par la vapeur générée par les fosses de lave), il était plus rapide d’utiliser des float . Maintenant, le seul avantage réel des fonds float est qu’ils prennent moins de place (ce qui ne compte que si vous en avez des millions).

J’ai eu un petit projet où j’ai utilisé CUDA et je me souviens que le float était plus rapide que le double. Pour une fois, le trafic entre Host et Device est plus faible (Host est le CPU et la RAM et le périphérique “normal” sont le GPU et la RAM correspondante). Mais même si les données résident sur l’appareil tout le temps, c’est plus lent. Je pense avoir lu quelque part que cela a changé récemment ou est censé changer avec la prochaine génération, mais je ne suis pas sûr.

Il semble donc que le GPU ne puisse simplement pas gérer la double précision en mode natif dans ces cas, ce qui expliquerait également pourquoi GLFloat est généralement utilisé plutôt que GLDouble.

(Comme je l’ai dit, c’est seulement dans la mesure où je me souviens, je suis tombé dessus tout en cherchant float vs double sur un processeur.)

Cela dépend du système 32 bits ou 64 bits . Si vous comstackz en 64 bits, le double sera plus rapide. Compilé en 32 bits sur 64 bits (machine et système d’exploitation), rendu plus rapide de 30%:

  public static void doubleTest(int loop) { Console.Write("double: "); for (int i = 0; i < loop; i++) { double a = 1000, b = 45, c = 12000, d = 2, e = 7, f = 1024; a = Math.Sin(a); b = Math.Asin(b); c = Math.Sqrt(c); d = d + d - d + d; e = e * e + e * e; f = f / f / f / f / f; } } public static void floatTest(int loop) { Console.Write("float: "); for (int i = 0; i < loop; i++) { float a = 1000, b = 45, c = 12000, d = 2, e = 7, f = 1024; a = (float) Math.Sin(a); b = (float) Math.Asin(b); c = (float) Math.Sqrt(c); d = d + d - d + d; e = e * e + e * e; f = f / f / f / f / f; } } static void Main(string[] args) { DateTime time = DateTime.Now; doubleTest(5 * 1000000); Console.WriteLine("milliseconds: " + (DateTime.Now - time).TotalMilliseconds); time = DateTime.Now; floatTest(5 * 1000000); Console.WriteLine("milliseconds: " + (DateTime.Now - time).TotalMilliseconds); Thread.Sleep(5000); } 

Il y a quand même des cas où les flottants sont préférables – avec le codage OpenGL par exemple, il est beaucoup plus courant d’utiliser le type de données GLFloat (généralement mappé directement sur float 16 bits) car il est plus efficace que GLDouble.