0
  • I have a generic interface that requires a read and key method. I want to use reflection to get an instance of each implementation.
  • Once I have a the implementation, I want to get it's key and store the key and the instance in a dictionary.
  • Eventually, I would have a method where I pass in a key and byte[], it would look the key up in the dictionary and use the instance that it retrieves to read the byte[] and return an object.
  • I hope this is understandable, if not I can answer questions in the comments.
  • This example only has int and string, but I'll have many more types in my real implementation.

The Goal

To have a dictionary with 2 entries stored as such:

  • 43, IRead<int> new Reader()
  • 61, IRead<string> new Reader()

public interface IRead<T>
{
    T Read(bool[] binary);
    int Key( T type );
}

public class Reader : IRead<int>, IRead<string>
{
    int IRead<int>.Read( byte[] binary )
    {
        // does stuff
        returns 4;
    }

    public int Key( int type ) { return 43; }

    string IRead<string>.Read( byte[] binary )
    {
        // does stuff
        returns "example";
    }

    public int Key( string type ) { return 61; }

    static StreamProcessor( )
    {
        // Here I want to get the definitions
    }
}
jacobvoller.com
  • 476
  • 7
  • 28
  • You can't tell based on the the interface `IRead` that an implementation will have a parameterless constructor. So how do you know that you'll be able to create an instance of each type that you find? – Scott Hannen Apr 15 '16 at 04:11
  • @ScottHannen I just want to cast Reader into the type defined in the dictionary – jacobvoller.com Apr 15 '16 at 04:16
  • It looks like you are looking for some kind of IoC container implementation. Have a look at [this](http://stackoverflow.com/questions/28509317/get-all-types-that-implement-an-interface-in-unity) question and the suggested answers. – Jeroen Heier Apr 15 '16 at 04:27

2 Answers2

0

Please, when you ask a question, post code that compiles. It makes life easier for everyone (perhaps your answer is because the pseudocode you wrote is wrong?)

In any case, this will get all types which implement IRead<>:

var types = GetType().Assembly.GetTypes()
.Select(t => new
{
    Type = t,
    MatchingInterfaces = t.GetInterfaces()
                          .Where(i => i.GetGenericTypeDefinition() == typeof(IRead<>))
})
.Where(t => t.MatchingInterfaces.Any())

Your pre-requisite of returning the key doesn't make that much sense. You can't find all instances of IRead<>. And you need an instance to give you a key.

For example, what would your dictionary look like if you had this code:

var readerOne = new Reader();
var readerTwo = new Reader();

Which instance goes into the dictionary?

The closest you can get is to:

  1. Pass the method a list of objects and return the key of those instances
  2. Create a dummy instance of each type to get the key
  3. Make the key method static, and not part of the interface.
Rob
  • 26,989
  • 16
  • 82
  • 98
0

I suggest breaking this up because there are a few different things you're trying to do - some are clear, some aren't.

First you want to get types that implement IReader:

public IEnumerable<Type> GetTypes<TAssignableFrom>()
{
    return this.GetType().Assembly.GetTypes()
        .Where(type => type.IsAssignableFrom(typeof (TAssignableFrom)));
}

What do you want to do with those types? If you want to create an instance of each type then either they need to have parameterless constructors or otherwise identical constructors, or you'd need to be using some dependency injection container.

Let's say that they're going to have parameterless constructors. We can update the above to

public IEnumerable<Type> GetTypes<TAssignableFrom>()
{
    return this.GetType().Assembly.GetTypes()
        .Where(type => type.IsAssignableFrom(typeof (TAssignableFrom))
            && type.GetConstructor(Type.EmptyTypes) != null
        );
}

Now you've got a bunch of types that you can instantiate.

From there it gets pretty fuzzy. What will you do with those types? It's not much use to put them into a dictionary because they are all different types.

Scott Hannen
  • 27,588
  • 3
  • 45
  • 62