سؤال

فعلت بعض توقيت الاختبارات و أيضا قراءة بعض المواد مثل هذا واحد (آخر تعليق) و يبدو في بيان بناء ، تعويم وضعف القيم تأخذ نفس الكمية من وقت المعالجة.

كيف يكون هذا ممكنا ؟ عندما تطفو هو أقل دقة وأصغر حجما مقارنة مزدوجة القيم ، كيف يمكن CLR على الزوجي في نفس المعالجة الوقت ؟

هل كانت مفيدة؟

المحلول

في معالجات x86، فإن كل تحويلها على الأقل، float وdouble إلى 10 بايت حقيقي من قبل FPU للمعالجة. وFPU لم يكن لديك وحدات معالجة منفصلة لمختلف أنواع الفاصلة العائمة التي يدعمها.

والنصيحة القديمة التي float أسرع من double تطبيقها قبل 100 سنة عندما كان معظم وحدات المعالجة المركزية لم قد بنيت في FPUs (وكان عدد قليل من الناس رقائق FPU منفصلة)، لذلك تم القيام به معظم التلاعب الفاصلة العائمة في مجال البرمجيات. على هذه الأجهزة (التي كانت تعمل بالبخار الناتجة عن الحفر الحمم البركانية)، فإنه <م> كان أسرع لاستخدام floats. الآن الاستفادة الحقيقية الوحيدة لfloats هو أنها تأخذ مساحة أقل (والذي يهم فقط إذا كان لديك الملايين منهم).

نصائح أخرى

وكان لي مشروع صغير حيث كنت CUDA وأتذكر كان أن تعويم أسرع من ضعف هناك، أيضا. لمرة واحدة على حركة المرور بين المضيف والجهاز أقل (المضيف هو وحدة المعالجة المركزية و "طبيعية" RAM والأجهزة هو GPU وRAM المقابل هناك). ولكن حتى لو توجد البيانات على الجهاز كل الوقت الذي أبطأ. أعتقد أنني قرأت في مكان ما أن هذا الوضع قد تغير في الآونة الأخيرة أو من المفترض أن تتغير مع الجيل القادم، ولكن لست متأكدا.

وهكذا يبدو أن GPU ببساطة لا يمكن التعامل مع الدقة المزدوجة أصلا في تلك الحالات، وهذا ما يفسر أيضا لماذا يستخدم GLFloat عادة بدلا من GLDouble.

و(كما قلت انها فقط بقدر ما أستطيع أن أتذكر، فقط تعثرت على هذا أثناء البحث عن تعويم مقابل ضعف على وحدة المعالجة المركزية).

ذلك يعتمد على 32 بت أو 64 بت النظام.إذا كنت تجميع 64 بت مزدوجة سوف يكون أسرع.جمعت إلى 32 بت على 64 بت (الجهاز ونظام التشغيل) مصنوعة تطفو حول 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);
    }

لا تزال هناك بعض الحالات التي يفضل يطفو ولكن - مع برنامج OpenGL الترميز على سبيل المثال انها أبعد ما تكون أكثر شيوعا في استخدام نوع البيانات GLFloat (تعيين عموما مباشرة إلى تعويم 16 بت) لأنها أكثر كفاءة في معظم وحدات معالجة الرسومات من GLDouble

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top