Type definition for superset of types

Suppose I have a basic inheritance structure:

public class Letter {...}
public class A : Letter {...}
public class B : Letter {...}
public class C : Letter {...}

public class Number {...} 
public class One : Number {...}

I want to define an array Type, so only Typethose that inherit from are valid Letter. So, an array of samples might look like this:

(type)[] myArray = new (type)[] {typeof(A), typeof(B), typeof(C)};

But the appointment

myArray[0] = typeof(One);

will fail. Is it possible to define such a structure?

+4
source share
3 answers

, : typeof System.Type. , , , . , , , .

:

  • , . :

    Type[] myArray = new (type)[] {typeof(A), typeof(B), typeof(C)};
    
    //...
    
    Contract.Ensures(Contract. ForAll (myArray,t => typeof(Letter).IsAassignableFrom(t));
    

    , .

  • (, ICollection<Type>, . :

    public class SubTypeList<T> : IList<Type> {
    
        private readonly List<Type> innerList = new List<Type>();
    
        public void Add (Type type) {
            if(typeof(T).IsAssignableFrom(type)) {
                innerList.Add(type);
            } else {
                throw new ArgumentException("The given System.Type must be an inherit from T!");
            }
        }
    
        //Implement other methods
        //...
    
    }
    
+1

System.Type, . . - , :

internal sealed class LetterTypeSet : IReadOnlyCollection<Type>
{
    readonly ISet<Type> types = new HashSet<Type>();
    public IEnumerator<Type> GetEnumerator() => this.types.GetEnumerator();
    IEnumerator IEnumerable.GetEnumerator() => this.GetEnumerator();
    public int Count => this.types.Count;

    public bool Add<T>()
        where T : Letter
    {
        return this.types.Add(typeof (T));
    }
}

:

var letters = new LetterTypeSet();
letters.Add<A>(); //ok
letters.Add<B>(); //ok
letters.Add<One>(); //CS0311 "The type 'One' cannot be used ..."

. ISet<T> , List<T> .

+3

Letter, Letter , , . , , , Letter. , . , , :

if (myArray[i] is A)
{
    A objA = myArray[i] as A;
    ...

is as downcasts, , downcast .

, , Letter, , , .

myArray[i].DrawSelf(Point ptStart)

and make the various derived classes responsible for knowing how to draw themselves, starting from a specific place.

0
source

Source: https://habr.com/ru/post/1623839/


All Articles