0

Currently i'm trying to parse a integer that is a bitwise combination to a enum from a third-party API. For example: i receive a integer with the value 1035 this value holds three enum values;

enum Status
    1= "Status 1" 
    2= "Status 2" 
    4= "Status 3" 
    8= "Status 4" 
    ........ 
    1024= "Status 8"
end enum

So i need a function that converts the value 1035 to Status 1 + Status 2 + Status 4 + Status 8

Tried to convert it to Bit and then use bit shifting but this doesn't give me the right results... Hopefully someone could help me out in C# or vb.net example.

Adriaan
  • 17,741
  • 7
  • 42
  • 75
Gforse
  • 323
  • 3
  • 20

4 Answers4

5

If you apply the [Flags] attribute to the enum, it will make the enum's ToString() return a string which indicates which bits are set - but I don't think that is going to be that useful to you, other than its role in documenting that the enum is a flags enum.

However, regardless of the presence of the [Flags] attribute, Enum.HasFlag() will tell you if the flag is set.

This sample console app should make it clear:

using System;

namespace Demo
{
    [Flags]
    enum Status
    {
        None     = 0,
        Status1  = 1,
        Status2  = 2,
        Status3  = 4,
        Status4  = 8,
        Status5  = 16,
        Status6  = 32,
        Status7  = 64,
        Status8  = 128,
        Status9  = 256,
        Status10 = 512,
        Status11 = 1024
    }

    class Program
    {
        static void Main()
        {
            Status s = (Status)1035;

            Console.WriteLine(s); // "Status1, Status2, Status4, Status11"

            if (s.HasFlag(Status.Status4))               // "Status 4 is set"
                Console.WriteLine("Status4 is set");
            else
                Console.WriteLine("Status4 is not set");

            if (s.HasFlag(Status.Status3))               // "Status 3 is not set"
                Console.WriteLine("Status3 is set");
            else
                Console.WriteLine("Status3 is not set");
        }
    }
}

Note: Your enum appears to be missing some values! The 1024 value should be Status11, not Status8.

Also note that I added a "None" value for completeness.

Matthew Watson
  • 104,400
  • 10
  • 158
  • 276
1

The bitwise operators can be used for this problem. (1<< i) gives 2 to the power "i". Then bitwise AND (&) with the "value" gives the nonzero number if and only if the corresponding power of two is present in the "value".

public static void GetFlags(int value)
{
    for (int i = 0; i < 20; i++)
    {
        if (((1 << i) & value) > 0)
            Console.WriteLine($"Status {i + 1} is present");
    }
}
L_J
  • 2,351
  • 10
  • 23
  • 28
  • 3
    While this code may answer the question, providing information on *how* and *why* it solves the problem improves its long-term value. – Thomas Flinkow Jun 05 '18 at 09:44
0

You can do this with the [Flags] attribute:

[Flags]
enum bla {
  foo = 1,
  bar = 2,
  baz = 4
}

public void Foo() {
  bla flag = (bla)3; // Flags foo and bar
  int andBackToInt = (int)flag; // 3

}
JAD
  • 2,035
  • 4
  • 21
  • 35
  • 1
    The `Flags` attribute only affects the output of the `ToString` method. It is the use of powers of 2 for the values that allows `enum` values to be combined. – jmcilhinney Jun 05 '18 at 07:51
  • @jmcilhinney Huh, interesting. TIL. Do you think this answer is worth leaving up then? – JAD Jun 05 '18 at 07:54
0

Thanks all for your quick responses, really appreciate it! :-)

The attribute was new for me. The third party enum has no flags aatribute thats why the Ctype to enum didn't return all values. So i ended up copying all the enums values (via the Object browser it was easy peasy) and creating a local enum WITH the flags attribute set. Now it converts just as i would hope!

Thanks all!

Gforse
  • 323
  • 3
  • 20