خوارزمية .Net مدمجة لتقريب القيمة إلى أقرب فاصل زمني 10

StackOverflow https://stackoverflow.com/questions/274439

  •  07-07-2019
  •  | 
  •  

سؤال

كيفية تقريب أي قيمة في C# إلى فاصل زمني 10؟على سبيل المثال، إذا كان لدي 11، أريد أن يعود 10، وإذا كان لدي 136، فأنا أريد أن يعيد 140.

يمكنني القيام بذلك بسهولة باليد

return ((int)(number / 10)) * 10;

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

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

المحلول

وليس هناك وظيفة المضمنة في مكتبة الفئة من شأنها أن تفعل هذا. الأقرب هو System.Math.Round () حيث هو فقط من أجل التقريب أعداد أنواع عشري ومزدوجة إلى أقرب قيمة عدد صحيح. ومع ذلك، يمكنك لف بيانكم حتى في طريقة التمديد، إذا كنت تعمل مع الصافي 3.5، والتي سوف تسمح لك لاستخدام وظيفة أكثر من ذلك بكثير نظيفة.

public static class ExtensionMethods
{
    public static int RoundOff (this int i)
    {
        return ((int)Math.Round(i / 10.0)) * 10;
    }
}

int roundedNumber = 236.RoundOff(); // returns 240
int roundedNumber2 = 11.RoundOff(); // returns 10

إذا كنت البرمجة ضد نسخة قديمة من .NET Framework، فقط إزالة "هذا" من وظيفة RoundOff، واستدعاء الدالة كما يلي:

int roundedNumber = ExtensionMethods.RoundOff(236); // returns 240
int roundedNumber2 = ExtensionMethods.RoundOff(11); // returns 10

نصائح أخرى

استخدم Math.Ceiling لجولة دائما.

int number = 236;
number = (int)(Math.Ceiling(number / 10.0d) * 10);

ومعامل (٪) يحصل على الباقي، حتى تحصل على:

// number = 236 + 10 - 6

ووضع ذلك في طريقة تمديد

public static int roundupbyten(this int i){
    // return i + (10 - i % 10); <-- logic error. Oops!
    return (int)(Math.Ceiling(i / 10.0d)*10); // fixed
}

// call like so:
int number = 236.roundupbyten();

وفوق تحريرها: ينبغي لقد ذهبت مع أول غريزة جهدي لاستخدام Math.Ceiling

كتبت عن هذا عند حساب الأرقام الاختيار UPC .

وهذا قد يكون قليلا في وقت متأخر جدا ولكن أعتقد أن هذا قد يكون مفيد جدا في يوم من الأيام ...

ولقد حاول هذا:

public int RoundOff(int number, int interval){
    int remainder = number % interval;
    number += (remainder < interval / 2) ? -remainder : (interval - remainder);
    return number;
}

لاستخدام:

int number = 11;
int roundednumber = RoundOff(number, 10);

وبهذه الطريقة، لديك الخيار ما إذا كان إذا كان النصف الفاصل الزمني سيتم تقريب أو تقريب لأسفل. =)

إن تقريب العدد إلى عدد صحيح يشبه (int)(x+0.5)، بدلاً من مجرد تحويل x - إذا كنت تريد مضاعفًا للرقم 10، فيمكنك تعديل ذلك بسهولة.

إذا كنت تريد فقط إجراء عمليات حسابية للأعداد الصحيحة وتقريبها إلى عشرة، فجرّب (x+10/2)/10*10.

يحرر: لقد لاحظت أن هذا الرد لا يلبي طلب المؤلف الأصلي، وهو أيضًا شكل من أشكال التقريب المتحيز الذي أفضل عدم القيام به.ومع ذلك، هناك رد مقبول آخر ذكر بالفعل Math.round()، وهو حل أفضل بكثير.

وقديم السؤال ولكن هنا هو وسيلة لتحقيق ما تم طلب زائد I تمديده لتكون قادرة على محاصرة أي رقم إلى عدد من التين سيج تريد.

    private double Rounding(double d, int digits)
    {
        int neg = 1;
        if (d < 0)
        {
            d = d * (-1);
            neg = -1;
        }

        int n = 0;
        if (d > 1)
        {
            while (d > 1)
            {
                d = d / 10;
                n++;
            }
            d = Math.Round(d * Math.Pow(10, digits));
            d = d * Math.Pow(10, n - digits);
        }
        else
        {
            while (d < 0.1)
            {
                d = d * 10;
                n++;
            }
            d = Math.Round(d * Math.Pow(10, digits));
            d = d / Math.Pow(10, n + digits);
        }

        return d*neg;
    }


   private void testing()
   {
       double a = Rounding(1230435.34553,3);
       double b = Rounding(0.004567023523,4);
       double c = Rounding(-89032.5325,2);
       double d = Rounding(-0.123409,4);
       double e = Rounding(0.503522,1);
       Console.Write(a.ToString() + "\n" + b.ToString() + "\n" + 
           c.ToString() + "\n" + d.ToString() + "\n" + e.ToString() + "\n");
   }

وأنا أفضل أن لا يحضر في المكتبة Math ولا تذهب إلى النقطة العائمة ذلك اقتراحي هو مجرد قيام عدد صحيح حسابية مثل أدناه حيث كنت محاصرة إلى 1K المقبل. التفاف عليه في طريقة أو امدا قصاصة أو شيء من هذا إذا كنت لا تريد تكراره.

int MyRoundedUp1024Int = ((lSomeInteger + 1023) / 1024) * 1024;

وأنا لم إجراء اختبارات الأداء على هذا مقابل الآخر الطرق ولكن كنت أراهن هو أسرع طريقة للقيام بذلك حفظ ربما تحول والدورية للنسخة أجزاء من هذا.

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