Saturday, February 5, 2011

Best way to find out if an (upcast) instance doesn't implement a particular interface

Maybe the need to do this is a 'design smell' but thinking about another question, I was wondering what the cleanest way to implement the inverse of this:

foreach(ISomethingable somethingableClass in collectionOfRelatedObjects)
{
  somethingableClass.DoSomething();
}

i.e. How to get/iterate through all the objects that don't implement a particular interface?

Presumably you'd need to start by upcasting to the highest level:

foreach(ParentType parentType in collectionOfRelatedObjects)
{
  // TODO: iterate through everything which *doesn't* implement ISomethingable 
}

Answer by solving the TODO: in the cleanest/simplest and/or most efficient way

  • Something like this?

    foreach (ParentType parentType in collectionOfRelatedObjects) {
        if (!(parentType is ISomethingable)) {
        }
    }
    
    From J D OConal
  • Probably best to go all the way and improve the variable names:

    foreach (object obj in collectionOfRelatedObjects)
    {
        if (obj is ISomethingable) continue;
    
        //do something to/with the not-ISomethingable
    }
    
  • J D OConal's is the best way to do this but as a side note, you can use the as keyword to cast an object, and it'll return null if its not of that type.

    So something like:

    foreach (ParentType parentType in collectionOfRelatedObjects) {
        var obj = (parentType as ISomethingable);
        if (obj == null)  {
        }
    }
    
    From sontek
  • this should do the trick:

    collectionOfRelatedObjects.Where(o => !(o is ISomethingable))
    
    J D OConal : Nice. I haven't done too much with these new methods.
    From Jay Bazuzi
  • With some help from the LINQ extension method OfType<>(), you can write:

    using System.Linq;
    
    ...
    
    foreach(ISomethingable s in collection.OfType<ISomethingable>())
    {
      s.DoSomething();
    }
    
    From Yacoder

0 comments:

Post a Comment