views:

42

answers:

3

Hi,

In C# it's possible to defined a method parameter with two interface restrictions. This with bounds. For example.

interface IA
{
  int A {get;}
}
interface IB
{
  int B {get;}
}
void Foo<T>(T param1) where T: IA, IB    {}

So two interfaces, and the first parameter (param1) of the method Foo should implement both interfaces.

But is this really useful? AFAIK it's not possible to cast an object to multiple interfaces in C#? Of course a class can implement two interfaces.

+3  A: 

You can certainly assign it to one at a time:

IA asIA = param1;
IB asIB = param1;

Further, you can use it as either, even without those lines (assume these take a IA or IB parameter, respectively)

IAFunc(param1);
IBFunc(param1);
Matthew Flaschen
@Keith, I don't follow. First of all, `Foo` is a method not a type, so "is a Foo" doesn't make sense. Second of all, neither `IAFunc` nor `IBFunc` has to know that param1 is also a IB or IA (respectively). They can just treat it as a regular instance of the type in their name.
Matthew Flaschen
Forget it. I see what you're trying to say you can do is within the context of Foo as a method.
KeithS
+2  A: 

This is very useful if the templatized class requires functionality from multiple interfaces. For instance maybe you require classes to be comparable to one another, IComparable, and you also want to make sure the user of your template class remembers to override ToString() so the data can be displayed, IFormattable.

That is somewhat of a contrived answer but being able to specify precise interfaces multiple times allow you to keep functionality in its interface without getting one cluttered.

linuxuser27
+3  A: 

Sometimes you have genericized logic which requires functionality from multiple types simultaneously. For example, I once had to perform the same logic on the Button, LinkButton, and ImageButton controls from ASP.NET. They each separately derive from WebControl and implement the IButtonControl interface; there is no base class which unites them.

I needed to wire a handler to the Click event, exposed by IButtonControl, and set a client click handler through the Attributes collection, which is exposed by WebControl. To enable a method which does both, my only choice was multiple type constraints:

private T CreateButton<T>() where T : WebControl, IButtonControl, new()
{
    var button = new T();

    button.Click += ...;

    button.Attributes["onClick"] = ...;

    return button;
}
Bryan Watts
+1 Great example.
linuxuser27