C#: الحصول على أدنى مفتاح قيمة في التعداد الصغير

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

  •  23-09-2019
  •  | 
  •  

سؤال

لدي تعداد مثل هذا

[Flags]
public enum Key
{
  None = 0,
  A = 1,
  B = 2,
  C = 4
}

لدي ما يلي

Key k1 = Key.A | Key.B | Key.C;

أريد الحصول على المفتاح في K1 الذي لديه أدنى قيمة. كيف أقوم بذلك؟

مثال:

Key k1 = Key.A | Key.B | Key.C; // I want a 
Key k2 = Key.B | Key.C; // I want b
Key k3 = Key.A | Key.C; // I want a
هل كانت مفيدة؟

المحلول

Keys key = Keys.b | Keys.c;

var lowest = Enum.GetValues(typeof(Keys))
    .Cast<Keys>()
    .OrderBy(x => x)
    .FirstOrDefault(x => key.HasFlag(x));

نسخة أكثر كفاءة و .net 4.0-ish من طريقة LINQ.

نصائح أخرى

يمكنك استخدام خدعة قليلا:

Key key = Key.B | Key.C;
Key lowest = (Key)((int)key & -(int)key);
Keys key = Keys.b | Keys.c;

var lowest = Enum.GetValues(typeof(Keys))
    .OfType<Keys>()
    .Where(x => (x & key) != 0)
    .OrderBy(x => x)
    .DefaultIfEmpty((Keys)0);

Console.WriteLine(lowest);

إذا كان لديك 3 قيم فقط في التعداد ، فربما يكون أسرع وأسهل هو التحقق منها واحدًا تلو الآخر. للحصول على حل عام ، قد ترغب في محاولة تحويل قيمة k1 إلى عدد صحيح ، ابحث عن أكبر قوة 2 التي تقسمها وتحويلها إلى قيمة تعداد المفاتيح.

  1. احصل على قائمة بجميع القيم في التعداد
  2. قم بتخطيط هذه القيم إلى نوع من أنواع البيانات القابلة للمقارنة
  3. قارن كل القيم وتتبع أقلها
  4. قم بتحويل أقل واحد إلى نوع التعداد

يجب أن يكون تطبيقًا تكراريًا حيث تختبر البتات. سأفعل شيئًا كهذا.

unsigned int k = (unsigned int) k1;
int pos = -1;
while (k) {
   pos++;
   if (k & 0x1) break;
   k >>= 1;
}
Keys lowestKey = 0;
if (pos >= 0) lowestKey = 0x1 << pos;

الرمز الذي نشرته في الأصل لا معنى له: لا يتم توجيه A+B+C بواسطة اسم النوع ، لذلك لن يشيروا إلى أسماء التعدادات التي يبدو أنها تهدف إلى الإشارة إليها.

وأيضًا ، إذا كنت تستخدم جزءًا صغيرًا وللجمع بين الأعلام ، فستتضمن النتيجة جميع الأعلام في الكل المعلمات - في هذه الحالة ، لا شيء.

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