Как получить не содержащие флаги - PullRequest
0 голосов
/ 20 сентября 2018

У меня есть флаги enum.Как получить все комбинации флагов, которые не содержат определенного?

[Flags]
public enum TestEnum
{
    A = 1,
    B = 2,
    C = 4,
    D = 8
}

public static IEnumerable<Enum> AllNotContaining(this Enum value)
{....}

Например, TestEnum.A.AllNotContaining() должно вернуть {2, 4, 6, 8, 10, 12, 14}.

Ответы [ 3 ]

0 голосов
/ 20 сентября 2018

Попробуй так:

public static IEnumerable<TestEnum> AllNotContaining(this TestEnum value)
{
    return Enum.GetValues(typeof(TestEnum)).Cast<TestEnum>().Where(x => x != value).AsEnumerable();
}
0 голосов
/ 20 сентября 2018

Я не пытался отшлифовать приведенный ниже код, но вы должны получить общее представление:

  public static IEnumerable<int> AllNotContaining<T>(this T value)
    // where T : Enum  (as of C# 7.3).
  {
    // Determine upper bound of values to check.
    // E.g. for your test enum, the maximum value is 8 so we need to check up to 15.
    var values = Enum.GetValues(typeof(T)).Cast<int>();
    int max = values.Max() * 2 - 1;

    // Test all values to see if the given flag is present. If not, return it.
    for(int i = 0; i <= max; ++i)
    {
      // Possibly also: if( ((Enum)i).HasFlags(value))
      if((max & Convert.ToInt32(value)) == 0)
      {
        yield return i;
      }
    }
  }
0 голосов
/ 20 сентября 2018

Шаг 1, используйте двоичный файл NOT:

var notUsedBits = ~ value;

Но это установит все 32 бита, которые не были использованы.

Таким образом, вы, вероятно, захотите маску:

[Flags]
public enum TestEnum
{
    A = 1,
    B = 2,
    C = 4,
    D = 8,    
    All = A|B|C|D,  // or compute this inside the method    
}

и затем метод становится

// untested
public static TestEnum AllNotContaining(this TestEnum value)
{
    return ~ value & TestEnum.All;
}

, это не возвращает IEnumerable, но это странно (и неэффективно) для перечисления Flags в любом случае.

...