0

I have 81 classes(still growing) which implement an interface, and I have a class that has a property that represents that interface ex:

public wrapper
{
   public Imyinterface instance{get;set;}

   public wrapper(string theNameOfTheClass)
   {
    instance = System.Reflection.Assembly.GetExecutingAssembly().CreateInstance(theNameOfTheClass);
    instance.Run(); //the interface has a run method
   }
}

is this the best way to go with, and how can I avoid reflection and not have to write any extra code?

Samuel
  • 6,126
  • 35
  • 70
user1492051
  • 886
  • 8
  • 22

2 Answers2

4

I'm not sure, but maybe:

public Wrapper<T>
   where T : IMyInterface, new()
{
    public IMyInstance instance { get; set; }

    public Wrapper()
    {
        instance = new T();
        instance.Run();
    }
}

Use it like:

Wrapper<SomeClass> wrapper = new Wrapper<SomeClass>();

If you want to keep the wrappers on some kind of list, simply derive them from common, non-generic class:

public abstract class BaseWrapper
{

}

public class Wrapper<T> : BaseWrapper
...

Edit: In response to comments

Maybe the problem is not in the wrapper class. If you get a string from user, you have only two options: either a giant switch or reflection.

You may change that for example by changing the ListBox contents:

public class ComboBoxItem
{
    public string Title { get; set; }
    public Func<IMyInterface> creator { get; set; }        

    public override string ToString()
    {
        return Title;
    }
}

Now create a list of these items and pass it to the ComboBox:

var items = new[] {
    new ComboBoxItem { Title = "First class", creator = () => new FirstClass() },
    new ComboBoxItem { Title = "Second class", creator = () => new SecondClass() },
}

You have to populate that ComboBox anyway, so there will be some hardcoding. The point is to hardcode the class list only in one place (maybe even in a place unrelated to the ComboBox, and then re-create ComboBox contents basing on that list).

Spook
  • 25,318
  • 18
  • 90
  • 167
  • but problem is i don't want to hard code, because there are too many classes, and and a wrapper instance is created based on the selected value from a listbox and it recives a string of the class name – user1492051 Apr 09 '14 at 10:58
  • populating the combobox is not a problem since the data is available in an sql database that is filled by a blond secretary ;) – user1492051 Apr 09 '14 at 11:06
  • 1
    If you have no way of matching strings with class types in the code, I guess you're out of options and you'll have to use reflection one way or another. You may do it a little bit nicer, as @MichalCiechan suggests. – Spook Apr 09 '14 at 11:08
1

Have a look at Unity IoC (or any other IoC that can resolve from string):

From IOC Container Runtime Resolution

string typeName = "MyTypeName";
var type = container.Registrations.FirstOrDefault(r => r.RegisteredType.Name == typeName);
if(type != null)
{
    var resolvedInstance = container.Resolve(type.RegisteredType);
}

EDIT: For Convention over Configuration have a look at the links at links in this question

Using Unity With Minimal Configuration

Community
  • 1
  • 1
Michal Ciechan
  • 13,492
  • 11
  • 76
  • 118
  • Ok, but you have to register these classes somewhere before using that, don't you? – Spook Apr 09 '14 at 11:04
  • Yes, but you can do convention over configuration. E.g. give it a namespace and/or assembly to look in, and it will register all classes from there. – Michal Ciechan Apr 09 '14 at 11:04
  • 1
    I know, where you're going, but this solution will effectively only delegate usage of the reflection to another class, won't it? :) – Spook Apr 09 '14 at 11:06