Implementing covariant interface multiple times: is this behavior properly defined? - c#

Given the following covariant generic interface
public interface IContainer<out T>
{
T Value { get; }
}
We can create a class that implements this interface multiple times for multiple generic types. In the scenario I'm interested about, these generic types share a common base type.
public interface IPrint
{
void Print();
}
public class PrintA : IPrint
{
public void Print()
{
Console.WriteLine("A");
}
}
public class PrintB : IPrint
{
public void Print()
{
Console.WriteLine("B");
}
}
public class SuperContainer : IContainer<PrintA>, IContainer<PrintB>
{
PrintA IContainer<PrintA>.Value => new PrintA();
PrintB IContainer<PrintB>.Value => new PrintB();
}
Now things get interesting when using this class through a reference of type IContainer<IPrint>.
public static void Main(string[] args)
{
IContainer<IPrint> container = new SuperContainer();
container.Value.Print();
}
This compiles and runs without issue and prints "A". What I've found in the spec:
The implementation of a particular interface member I.M, where I is
the interface in which the member M is declared, is determined by
examining each class or struct S, starting with C and repeating for
each successive base class of C, until a match is located:
If S
contains a declaration of an explicit interface member implementation
that matches I and M, then this member is the implementation of I.M.
Otherwise, if S contains a declaration of a non-static public member
that matches M, then this member is the implementation of I.M.
The first bullet point appears to be relevant, because the interface implementations are explicit. However, it doesn't say anything about which implementation is selected when there are multiple candidates.
It gets even more interesting if we use a public poperty for the IContainer<PrintA> implementation:
public class SuperContainer : IContainer<PrintA>, IContainer<PrintB>
{
public PrintA Value => new PrintA();
PrintB IContainer<PrintB>.Value => new PrintB();
}
Now, according to above spec, because there is an explicit interface implementation through IContainer<PrintB>, I would expect this to print "B". However, it is instead using the public property and still printing "A".
Similarly, if instead I implement IContainer<PrintA> explicitely and IContainer<PrintB> through public property, it still prints "A".
It appears that the only thing the output depends on is the order in which the interfaces are declared. If I change the declaration to
public class SuperContainer : IContainer<PrintB>, IContainer<PrintA>
everything prints "B"!
Which part of the spec defines this behavior, if it is properly defined at all?

I'm unable to find it in the specification, but what you're seeing is expected. IContainer<PrintA> and IContainer<PrintB> have different Fully Qualified Names (unable to find spec on how this FQN is formed) and so the compiler recognizes SuperContainer as an implementing class of two different interfaces, each having a void Print(); method.
So, we have two different interfaces each containing a method with the same signature. As you linked in the spec (13.4.2) the implementation of Print() is chosen first by looking at IContainer<PrintA>, looking for a proper mapping, and then looking at IContainer<PrintB>.
Since a proper mapping was found in IContainer<PrintA>, IContainer<PrintA>.Print() is used in SuperContainer's implimentation of IContainer<PrintB>.
From that same spec (located at the very bottom):
The members of a base class participate in interface mapping. In the example
interface Interface1
{
void F();
}
class Class1
{
public void F() {}
public void G() {}
}
class Class2: Class1, Interface1
{
new public void G() {}
}
the method F in Class1 is used in Class2's implementation of Interface1.
So in the end, yes the order is determining which Print() method is called.

Related

Call a class function from an explicit interface function with the same name

The attached code works as expected, it prints 'Something!',
but is it defined behaviour (to call the 'normal' method from the 'explicit' method)?
I have searched for various combinations of 'explicit interface call method/function', but all I could find were examples about the difference between implicit and explicitly defined interface functions, and how to call an explicitly defined function.
interface ISomething
{
void DoSomething();
}
class Something : ISomething
{
private void DoSomething()
{
Console.WriteLine("Something!");
}
void ISomething.DoSomething()
{
DoSomething();
}
public static void Main()
{
ISomething thing = new Something();
thing.DoSomething();
}
};
Your code will have the same output no matter how things work. I suggest using next for clearer understanding:
class Something : ISomething
{
private void DoSomething()
{
Console.WriteLine("Something!");
}
void ISomething.DoSomething()
{
Console.WriteLine("Explicit Something!");
}
};
Which will print Explicit Something! for your Main. As for why for both implementations - as draft C# 7.0 specification states:
It is not possible to access an explicit interface member implementation through its qualified interface member name in a method invocation, property access, event access, or indexer access. An explicit interface member implementation can only be accessed through an interface instance, and is in that case referenced simply by its member name.
So DoSomething() call in original ISomething.DoSomething() implementation is call to the Something.DoSomething() and not to ISomething.DoSomething(). ISomething.DoSomething() is no accessible cause it requires an interface instance. If you rename ISomething.DoSomething to for example ISomething.DoSomething1 you will see that it is not accessible inside ISomething.DoSomething1 call unless you cast this to interface:
interface ISomething
{
void DoSomething1();
}
class Something : ISomething
{
public void DoSomething()
{
Console.WriteLine("Something!");
}
void ISomething.DoSomething1()
{
// DoSomething1(); // The name 'DoSomething1' does not exist in the current context
// ((ISomething)this).DoSomething1(); // will obviously end in SO
Console.WriteLine("ISomething.DoSomething1!");
}
}
Also can be useful interface mapping section:
Notable implications of the interface-mapping algorithm are:
Explicit interface member implementations take precedence over other members in the same class or struct when determining the class or struct member that implements an interface member.
Neither non-public nor static members participate in interface mapping.

Understanding Interfaces C#

Been reading all day on interfaces and abstract classes trying to get a grasp on them to better understand the amazon library I'm working with. I have this code:
using MWSClientCsRuntime;
namespace MarketplaceWebServiceOrders.Model
{
public interface IMWSResponse : IMwsObject
{
ResponseHeaderMetadata ResponseHeaderMetadata { get; set; }
}
and
namespace MWSClientCsRuntime
{
public interface IMwsObject
{
void ReadFragmentFrom(IMwsReader r);
string ToXML();
string ToXMLFragment();
void WriteFragmentTo(IMwsWriter w);
void WriteTo(IMwsWriter w);
}
}
My first questions is I thought Interfaces cannot contain fields, however they can contain properties usch as ResponseHeaderMetadata?
Second, in my main program I have this line of code:
IMWSResponse response = null;
with response being later used to store the information that amazon sends back after a method call is invoked. But what is the meaning behind setting a variable of an interface type to null?
Also, a interface can implement another interface? It isn't only classes that can implement interfaces, but interfaces themselves as well?
Pproperties can be present in interfaces since properties are actually methods - the use of T GetSomeValue() alongside void SetSomeValue(T value) became so common in other languages, that C# implements these as properties.
The meaning behind setting an interface member to null is the same as setting anyother property to null - since a property's set accessor is a method, it's like calling any other method on the interface. What null means where is up to the implementation.
Interfaces do not implement each other, since and interface cannot contain code and therefore is not implementing; Interface inheritance allows one to require one interface in another. A big example is IEnumerable<T>, which is so closely tied to IEnumerable that it inherits, thus meaning any class implementing IEnumerable<T> must also implement IEnumerable.
An interface is like a contractual agreement. By inheriting an interface from a class, you are saying, "I agree to implement all of the methods defined in this interface". So if you have an interface like this:
public interface IWorker {
void DoWork();
}
and you use that interface like this:
public class Employee : IWorker
{
// you are forced to implement this method
void DoWork {}
}
public class Contractor: IWorker
{
// you are forced to implement this method
void DoWork {}
}
By "inheriting" interfaces by other interfaces, you are simply agreeing to implement any methods in the other interfaces, like so (from MSDN):
interface IBase
{
void F();
}
interface IDerived: IBase
{
void G();
}
class C: IDerived
{
void IBase.F() {...}
void IDerived.G() {...}
}
class D: C, IDerived
{
public void F() {...}
public void G() {...}
}
You do not have to set a variable of an interface type to null, though you have the power to do so. The great thing about interfaces is that you are able to set a variable of the type of interface, to anything that "inherits" that interface.

C# Multiple Interface Inheritance does not allow public access modifier with same name

So this has me perplexed.
Suppose two interfaces.
public interface a
{
void foo();
}
public interface b
{
void foo();
}
Both of those interfaces have a function foo, I have a class that provides explicit implementation:
public class alpha : a, b
{
// why can't I put an access modifier here?
// How would you be able to hide this from a derived class
void a.foo()
{
Console.WriteLine("a");
}
void b.foo()
{
Console.WriteLine("b");
}
}
And a Class that is derived from alpha
public class beta : alpha
{
}
How do you make foo private or protected since alpha doesn't allow access modifiers on explicit imlementation, what can stop someone from calling:
var be = new beta();
(be as b).foo();
EDIT
How come when I don't explicitly provide implementation I can provide an access modifier?
public class alpha : a, b
{
//why this compile?
public void foo()
{
Console.WriteLine("both");
}
}
Since interface a is public, any class that implements a must make the methods of a publicly accessible, either implicitly (through public methods) or explicitly. Explicit implementations are "sort-of" private since they can only be accessed through the interface.
In short, there is no way to completely "hide" foo - your class implements both a and b so those methods must me made accessible through some means.
This would be true even if you only had one interface - having multiple interfaces with a method name collision just forces you to make the implementations explicit. If you had one interface, foo would either have to be public or explicit.
what can stop someone from calling
Nothing, that's the whole point!
beta is a b and thus you can treat it as a b. If you choose to cast it to b and call the explicit foo implementation you'll get b implementation.
As shown in other answers theses are rules of the language and had to be followed.
Sample showing why explicitly specifying public on interface implementation is required:
class Base
{
protected void Foo() { }
}
public interface IFoo
{
void Foo();
}
Class Base explicitly made choice to not expose method Foo to users of the class (except derived, could be private too).
Now if another class wants to derive from Base and implement IFoo at the same time. If language would allow to just pick implementations irrespective of access modifiers it would mean that Base.Foo is now exposed by derived to every caller:
class Derived : Base, IFoo
{
// hypothetical compiler allows to pick any matching `void Foo`
// including inherited `protected void Base.Foo()`
}
This would be clearly against intent of Base class to hide Foo method - so language have to require Foo to be public to be considered as part of interface.
As result you end up with "optional" access modifier on interface implementation where you have exactly one option - must specify public.
Note that Derived has couple options to deal with Foo - explicit implementation and shadowing with new:
class Derived : Base, IFoo
{
new public void Foo() {}
}

Accessing objects through their interfaces

What does it really mean? I am reading design pattern book. It says
objects are accessed solely through their interfaces, and I am not able to get my head around it, can some body give me an example (Will really appreciate if its in C#)
What do we really achieve by using it?
Thanks
If you have a class called Espson and it implements an interface called IPrinter then you can instantiate the object by it's interface.
IPrinter printer = new Espson();
Epson may have a number of methods that are not part of the IPrinter interface but you may not care. All you may want to do is call a method defined in the IPrinter interface called Print
So then I can pass the class to a method called PrintDocument(IPrinter printer) and the method doesn't care what type of printer it is, it just knows it has a method called Print
The problem is the interface has several meanings. In this case the author is talking that objects must be accessed through public methods (in C# through public properties also) only.
(Of course, inheritors may use protected methods).
Public methods/properties form the public interface of a class. It's not the same interface that described by interface keyword in C#.
That really depends. If the variable is of type "interface", then in that case the object can be accessed by the interface type only.
Let's consider an example - Suppose I have an interface as defined below -
interface IMyInterface
{
string B();
}
and if I implement this interface using a class "MyClass" as shown below -
public class MyClass:IMyInterface
{
public string B()
{
return "In Class";
}
}
public class MyAnotherClass:IMyInterface
{
public string B()
{
return "In Another Class";
}
}
and I create an instance of the class using the interface as shown below
IMyInterface myinst = new MyClass();
then in the above case I can only get access to the Method B() using variable myinst which contains a reference to MyClass type.
Going further, let's say I have a method that takes a parameter of type IMyInterface as shown below -
public class UseOfInterface{
public void InterfaceUse(IMyInterface myPara)
{
myPara.B();
}
}
and I call this method as shown below -
IMyInterface myInst = new MyClass();
IMyInterface myAnotherInst = new MyAnotherClass();
UseOfInterface interfaceUse = new UseOfInterface();
interfaceUse.InterfaceUse(myInst); // returns "In Class"
interfaceUse.InterfaceUse(myAnotherInst); // returns "In Another Class"
Then, as shown above, it is decided at runtime as to which method is called using the Interface variable.
But if I had created a variable of type MyClass which would have contained a reference of type MyClass itself as shown below -
MyClass myinst = new MyClass();
then method B() can be accessed using the MyClass instance. So it depends what type of scenario you are dealing with.
Edit: Why Use Interfaces?
The main reason to use an interface is that it provides a contract to the class for which it is being implemented apart from the multiple inheritance support in C#. Let's can see an example where the contract providing can be helpful.
Suppose you have a class - "Car" in your assembly that you want to expose publicly, the definition of the class is as shown below
namespace CarNameSpace
{
public class Car()
{
public void Drive(IDriver driver)
{
if(driver.Age > 18)
{
driver.Drive();
}
}
}
}
As shown above, anyone who implements the IDriver interface can drive the car, which is defined below,
interface IDriver
{
string Age{get; set;}
string Name {get set;}
string Drive()
}
In turn to drive my car I would be exposing the IDriver interface to the outer world, so anyone who implements my interface can call the Car's Drive method, doesn't matter how he drives the car as shown below
public class PerfectDriver:IDriver
{
public PerfectDriver()
{
Name = "Vikram";
Age = 30;
}
public int Age{get; set;}
public string Name {get; set;}
public string Drive()
{
return "Drive's perfectly";
}
}
The Car class can be used as shown below
PerfectDriver perf = new PerfectDriver
Car myCar = Car();
myCar.Driver(perf);
An interface is a construct that describes the signature of the public members of an object. It contains declarations (declarations only, no implementation) of properties, methods and events that are guaranteed to be present on any object that implements that interface.
Here's a simple interface and a few classes that implement it. The interface "INamed" states simply that objects implementing the interface have a "Name" property that is a string.
public interface INamed{
string Name{get;}
}
public class Person : INamed{
public string Name{get;set;}
}
public class Place : INamed{
public string Name{get;set;}
}
public class Thing : INamed{
public string Name{get;set;}
}
...And a simple method that accepts a parameter of that interface type.
static void PrintName(INamed namedObject){
Console.WriteLine(namedObject.Name);
}
This "PrintName" method can accept a parameter of any type that implements that interface. The advantage of "accessing objects by their interface" is that it infuses your application with a certain flexibility, accessing these interfaces as opposed to their concrete types allows you to operate on these objects without having to know what they really are.
I could, for instance choose to operate on the IDbCommand interface as opposed to a concrete SqlCommand and much of what I write in this manner will be useful when working with a variety of database providers.
The simple idea is that you don't need to know if you're in a car or a boat because you can drive anything with a wheel and pedals.
The interface refers to what the object exposes to users of the object. An object will be an instance of a class which will have its own interface and possibly implement one or more other interfaces.
While languages such as C# allow you to define things called interfaces, those are distinct from the interface referred to in the statement that objects are accessed through their interfaces. In a language such as Scala, for instance, what C# calls an interface is called a trait. Most design patterns do involve the use of defined interfaces, i.e. public interface <interface name>, but again, those are distinct from what is meant in the original statement.
Suppose I define the following class in C#:
public class MyType
{
public void Method1()
{
...
}
private void Method2()
{
...
}
public int Method3()
{
...
}
}
Then the interface through which I interact with the class is the two methods it exposes, void Method1 and int Method2 and the implicit parameterless constructor.
Now, suppose I define the following interfaces and class:
public interface IInterface1
{
void Method1();
}
public interface IInterface2
{
int Method3();
}
public class MyType2 : IInterface1, IInterface2
{
public void Method1()
{
...
}
private void ADifferentMethod()
{
...
}
public int Method3()
{
...
}
}
The interface through which a user interacts with instances of MyType2 is the same as that through which a user interacts with instances of MyType1 (except for the different constructors) because the signatures of the public methods (and other public members) are identical : void Method1 and int Method3.

Different behaviour of method overloading in C#

I was going through C# Brainteasers (http://www.yoda.arachsys.com/csharp/teasers.html) and came across one question: what should be the output of this code?
class Base
{
public virtual void Foo(int x)
{
Console.WriteLine ("Base.Foo(int)");
}
}
class Derived : Base
{
public override void Foo(int x)
{
Console.WriteLine ("Derived.Foo(int)");
}
public void Foo(object o)
{
Console.WriteLine ("Derived.Foo(object)");
}
}
class Test
{
static void Main()
{
Derived d = new Derived();
int i = 10;
d.Foo(i); // it prints ("Derived.Foo(object)"
}
}
But if I change the code to
class Derived
{
public void Foo(int x)
{
Console.WriteLine("Derived.Foo(int)");
}
public void Foo(object o)
{
Console.WriteLine("Derived.Foo(object)");
}
}
class Program
{
static void Main(string[] args)
{
Derived d = new Derived();
int i = 10;
d.Foo(i); // prints Derived.Foo(int)");
Console.ReadKey();
}
}
I want to why the output is getting changed when we are inheriting vs not inheriting; why is method overloading behaving differently in these two cases?
As I specified in the answers page:
Derived.Foo(object) is printed - when choosing an overload, if there are any compatible
methods declared in a derived class, all signatures declared in the base class are ignored
- even if they're overridden in the same derived class!
In other words, the compiler looks at methods which are freshly-declared in the most derived class (based on the compile-time type of the expression) and sees if any are applicable. If they are, it uses the "best" one available. If none is applicable, it tries the base class, and so on. An overridden method doesn't count as being declared in the derived class.
See sections 7.4.3 and 7.5.5.1 of the C# 3 spec for more details.
Now as for exactly why it's specified like that - I don't know. It makes sense to me that methods declared in the derived class take precedence over those declared in the base class, as otherwise you run into the "brittle base class" problem - adding a method in the base class could change the meaning of code using the derived class. However, if the derived class is overriding the method declared in the base class, it's clearly aware of it, so that element of brittleness doesn't apply.
It revolves around scope. In the first program, void Foo(int i) belongs to class Base. class Derived merely redefines its behavior.
Foo(int i) is ignored because it's being "borrowed" and redefined via inheritance from class Base. if Foo(object o) did not exist, then Foo(int i) would be used.
In the second program, void Foo(int i) is called because it properly belongs to class Derived (i.e. it's not being borrowed and overriden through inheritance) and has the best signature fit.
It's because the methods signatures in the derived class are matched first before considering the base class signatures. Therefore, when you try:
d.Foo(i);
It attempts to match the method signature against your current class (not the base class). It finds an acceptable match Foo(object) and doesn't further consider the base class method signatures.
It's all about the compiler finding a matching method signature, and the search order it uses to find these signatures.
-Doug

Categories