Использование другого типа в перечислении C # - PullRequest
3 голосов
/ 28 декабря 2011

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

public enum EnumWeapons
{
    Fists = new WeaponFists(),
    Sword = new WeaponSword(),
    Bow = new WeaponBow(),
    Staff = new WeaponStaff()
}

которые получены из оружия базового класса.

Можно ли использовать перечисление таким образом?

Если это так, смогу ли я сделать что-то вроде следующего? :

public Weapon weapon = (Weapon)EnumWeapons.Fists;

Мои попытки не сработали, как задумано, и любая помощь или руководство приветствуются :). Спасибо!

Ответы [ 9 ]

10 голосов
/ 28 декабря 2011

Это невозможно, базовым типом enum являются различные целочисленные типы.Из документации :

Допустимые типы перечислений: byte, sbyte, short, ushort, int, uint,long, или ulong.

Кроме того, я даже не думаю, что то, что вы пытаетесь сделать, имеет смысл.Когда вы хотите оружие, вы действительно хотите один и тот же экземпляр каждый раз?Я сомневаюсь в этом.

То, что вы действительно хотите, я думаю, это фабрика.В его самой наивной форме вы можете сказать:

public enum WeaponType {
    Fists,
    Sword,
    Bow, 
    Staff
}

public class WeaponFactory {
    public Weapon Create(WeaponType weaponType) {
        switch(weaponType) {
            case WeaponType.Fists:
                return new WeaponFists();

            case WeaponType.Sword:
                return new WeaponSword();

            case WeaponType.Bow:
                return new WeaponBow();

            case WeaponType.Staff:
                return new WeaponStaff();

            default:
                throw new ArgumentOutOfRangeException("weaponType");
        }
    }
}

Теперь вы можете сказать:

var weapon = weaponFactory.Create(WeaponType.Fists);
6 голосов
/ 28 декабря 2011

Нет, перечисления должны быть целочисленного типа (byte, short, int, long).

То, что вы пытаетесь сделать, может быть достигнуто так:

public static class EnumWeapons
{
    public static readonly Weapon Fists = new WeaponFists();
    public static readonly Weapon Sword = new WeaponSword();
    public static readonly Weapon Bow = new WeaponBow();
    public static readonly Weapon Staff = new WeaponStaff();
}
2 голосов
/ 28 декабря 2011

Код, который вы ввели, содержит объекты, и это больше не перечисление, которое является целью конструкции enum.Я не хочу повторять только то, что говорили другие, так что вот предложение: вы можете сохранить перечисление, но создать вспомогательный метод для генерации объектов Оружия, как это:

public enum EnumWeapons
{
    Fists,
    Sword,
    Bow,
    Staff
}

public Weapon EnumWeaponsToWeaponObject(EnumWeapons weapon)
{
        switch (weapon)
        {
            case EnumWeapons.Fists:
                return new FistWeapon();
                break;
            case EnumWeapons.Sword:
                return new SwordWeapon();
                break;
            case EnumWeapons.Bow:
                return new BowWeapon();
                break;
            case EnumWeapons.Staff:
                return new StaffWeapon();
                break;
            default:
                throw new ArgumentException("Not a supported weapon type!");
                break;
        }

}

Вы можете сделать этот метод расширением так,что вы можете использовать его следующим образом: EnumWeapons.Sword.EnumWeaponsToWeaponObject ();

2 голосов
/ 28 декабря 2011

Согласно этому источнику интегральные константы (что делает этот код недействительным на двух уровнях)

Вы можете использовать синтаксический сахар и сделать его похожим на перечисление:

public static class Weapons
{
    Weapon Fists = new WeaponFists(),
    Weapon Sword = new WeaponSword(),
    Weapon Bow = new WeaponBow(),
    Weapon Staff = new WeaponStaff()
}
2 голосов
/ 28 декабря 2011

Вы не можете использовать перечисление таким образом.Однако вы можете добиться чего-то похожего, создав статический класс:

public static class AllWeapons
{
    public static readonly Weapon Fists = new WeaponFists();
    // etc
}

Weapon weapon = AllWeapons.Fists;
2 голосов
/ 28 декабря 2011

Это не будет работать с перечислениями напрямую.Однако вы могли бы использовать «обычное» перечисление и Dictionary<EnumWeapons, Weapon> вместо этого, чтобы получить свои экземпляры оружия по значению перечисления.

1 голос
/ 28 декабря 2011

Вы можете использовать индексатор для обращения к массиву или списку как по порядковому номеру, так и по строке. Не так чисто, как перечисление, но Array или List могут содержать объекты. Это то, что делает его индексатором.

    namespace Indexer
    {
        class Program
        {
            static void Main(string[] args)
            {
                Persons MyPeople = new Persons();
                Console.WriteLine("MyPeople[0] " + MyPeople[0].Name);
                Console.WriteLine("MyPeople[0] " + MyPeople[1].Name);
                Console.WriteLine("MyPeople[Jim] " + MyPeople["Jim"].Name);
                Console.ReadLine();
            }
        }
        public class Persons
        {
            private List<Person> persons = new List<Person>();
            public int Count { get { return persons.Count; } }

            public Person this[int index]
            {
                get
                {
                    return persons[index];
                }
                set
                {
                    persons[index] = value;
                }
            }
            public Person this[string name]
            {
                get
                {
                    foreach (Person p in persons)
                    {
                        if (p.Name == name) return p;
                    }
                    return null;
                }
            }
            public Persons()
            { 
                persons.Add(new Person("Jim"));
                persons.Add(new Person("Harry"));
            }
            public class Person
            {
                private string name;
                public string Name { get { return name; } }
                public Person(string Name) { name = Name; }
            }
        }
    }
1 голос
/ 28 декабря 2011

Согласно MSDN, "Допустимые типы для перечисления: byte, sbyte, short, ushort, int, uint, long или ulong. "

См. Эту ссылку .

1 голос
/ 28 декабря 2011

Я не думаю, что перечисления C # работают таким образом. в C # все значения перечисления в основном целочисленные. Однако вы можете использовать свой подход:

public class Weapon 
{
    public static readonly Weapon Fists = new WeaponFists();
    public static readonly Weapon Sword = new WeaponSword();
   ...
}

, а затем

var myWeapon = Weapon.Fists;
...