Назначение нескольких значений элементам перечисления

Привет, у меня есть это перечисление в настоящее время

[Serializable]
public enum Country
{
    US      = 1,
    Canada  = 2,
}

Когда я обычно получаю целое число из базы данных, я конвертирую его в перечисление с помощью

(Country) Convert.ToInt32("1")

Теперь у меня есть 2 субрегиона в США и Канаде, 1 и 2 для США и 3 и 4 для Канады. Поэтому, когда я делаю

(Country) Convert.ToInt32("1") или (Country) Convert.ToInt32("2"), я должен получить перечисление как US. и для 3 и 4 Канады. Как это реализовать?

[Serializable]
public enum Country
{
    US      = 1,2
    Canada  = 3,4
}

Что-то вроде этого. Это, вероятно, не так, но только для того, чтобы дать вам Идею.

Ответ 1

А я просто использовал функцию вместо прямого приведения типов. Намного легче, чем реализовать что-то совершенно другое. У меня уже есть много кода, работающего на этом, поэтому я могу его немного изменить, но вот что я сделал.

public Country GetCountryByTaxID(int taxID)
        {
            if (taxID == 3 || taxID == 4)
            {
                return Country.USA;
            }
            else 
            {
                return Country.Canada;
            }
        }  

Ответ 2

enum может не быть правильной конструкцией для моделирования этой проблемы.

Я бы предложил создать класс для представления информации о стране и предоставить методы преобразования в числовые представления и из них. С такими проблемами вы также должны решить, какое значение кодирования вы будете использовать при преобразовании выбранного экземпляра страны в числовое значение.

Шаблон объекта Enum может быть полезной отправной точкой для моделирования такой ситуации:

public sealed class Country
{
    // initialize appropriately in the constructor...
    private readonly int[] m_Values;
    private readonly string m_Name;

    // make the constructor private so that only this class can set up instances
    private Country( string name, int[] codes ) { ... }

    public static Country US = new Country("United States", new[]{ 1,2 } );
    public static Country Canada = new Country("Canada", new[] {3,4} );

    public static Country FromCode( int code ) { ... }
    public override string ToString() { return m_Name; }
    // ... etc...
}

На основе вашего примера вы также должны подумать о том, нужно ли моделировать субрегионы страны как первоклассные сущности, а не просто складывать их в детали реализации вашей страны. Независимо от того, будете ли вы это делать или нет, зависит от ваших требований и вариантов использования, поэтому вы можете принять соответствующее решение.

Ответ 3

Вам нужно будет сделать что-то вроде этого:

class Region
{
    static readonly RegionMap = new Dictionary<int,string>
    {
        { 1, "US" },
        { 2, "US" },
        { 3, "Canada" }
        { 4, "Canada" }
    }

    public static string GetRegion(int code)
    {
        string name;
        if (!RegionMap.TryGetValue(code, out name)
        {
            // Error handling here
        }
        return name;
    }
}

Затем найдите строку на основе значения из базы данных:

string region = Region.GetRegion(dbVal);

Ответ 4

Это невозможно. Тогда вам придется использовать отдельные значения. Если имена совпадают, т.е.

[Serializable]
[Flags]
public enum Country
{
    US      = 1,
    Canada  = 2,
    Northern = 4,
    Southern = 8
}

Вы можете сделать это: Countries = Country.US | Country.Northern. Если нет, вам нужно найти другой способ, возможно другое свойство или даже лучше, класс Location.

Ответ 5

Может быть, что-то вроде этого?

static Country ConvertRegionToCountry(string region)
{
    switch (region)
    {
        case "1":
        case "2":
            return Country.US;

        case "3":
        case "4":
            return Country.Canada;
    }
}

Ответ 6

public Country GetCountry(int a)
        {
            if (a == 1 || a == 2)
            {
                return Country.USA;
            }
            else if (a ==  4|| a == 3)
            {
                return Country.Canada;
            }
        }  

Ответ 8

В дополнение к ответу dtb (и тем эквивалентным предложениям if) я просто внедрил "переопределенную" версию System.Convert в пространстве имен приложений:

public static class Convert
{
    public static object ChangeType
        (object value, Type conversionType, IFormatProvider provider)
    {
        int country;
        if (conversionType == typeof(Country)
            && int.TryParse(value.ToString(), out country))
        {
            switch (country)
            {
                case 1:
                case 2:
                    return Country.US;
                case 3:
                case 4:
                    return Country.Canada;
            }
        }

        // For most cases, including any country unmatched above...
        return System.Convert.ChangeType(value, conversionType, provider);
    }
}

Оригинальные методы класса mscorlib.dll Convert теперь должны иметь префикс "System.", конечно, поэтому любые уточнения будут приветствоваться!