C# Interfaces

The term interface has been used to describe the public interface of a class. The public interface contains methods, properties, indexers and other items that can be accessed by other classes. In this article, a second, related definition of interface is considered.
An interface is a code structure that is similar to an abstract class that has no concrete members. An interface can contain public members such as properties and methods but these members must have no functionality.
Instead, like abstract members, they define items that must be made concrete within all classes that implement the interface. This means that an interface can be used to define what a class must do, but not how it will achieve it.
Many classes may implement a single interface. This increases polymorphism by enabling classes to behave in many different ways depending upon their usage. For example, a Customer class, an Employee class and a Business class may all implement the IWriteable interface. If this interface contains properties describing an address, a method that accepts an IWriteable object as a parameter can be used to send a letter to any of these entity types. NB: The “I” prefix for an interface is a recognized naming convention.
Unlike with the single inheritance provided by C#, a class may implement many interfaces. These may be implemented in addition to inheritance from a base class. This combination provides a simplified variation upon the multiple inheritance concept that is not available to .NET programmers.

When to Choose an Interface or Abstract Class
Interfaces and abstract classes have similar purposes. Generally, an interface should be used when the implementation of the members it defines is not fixed, or when it is known that a single class requires the contents of several interfaces. Where the functionality of some members is fixed and the limited multiple inheritance facility is not required, abstract classes may be more appropriate.

Creating Interfaces
To demonstrate the use of interfaces we will create several and apply them to a group of classes. In this article we will define interfaces and classes that represent predators and prey animals. Each animal class will implement at least one of the IPredator and IPrey interfaces.
To begin, create a new console application named “InterfacesDemo”.

Declaring an Interface
An interface is declared in a similar manner to a class. The definition of the interface appears in a namespace, or within the default namespace. The interface’s name is prefixed with the interface keyword and requires a code block to contain the members that it defines.

interface interface-name {}

The first interface that we will create will be implemented by all animals that are prey to predators. To use the convention for interface naming, this interface will be called “IPrey”. To create the interface, add a new interface file to the project named “IPrey”. If your preferred development environment does not include a template for interfaces, simply add a class file and adjust the declaration of the class to match that shown below:

interface IPrey
{
}

Creating an Interface Property
When a property is added to an interface it acts as a placeholder only, containing no functionality of its own.
The functionality is added by the individual classes that implement the interface. Interface property declarations are therefore comparable to abstract property declarations and use a similar get and set accessor syntax. However, as all members of interfaces are public by definition, the “public” keyword is omitted.
The following code shows examples of read-write, read-only and write-only interface properties:

int ReadWriteProperty { get; set; }
int ReadOnlyProperty { get; }
int WriteOnlyProperty { set; }

The IPrey interface will define a property to hold the fleeing speed of prey animals. This is an important value when an animal must run away from a predator. To create the property, add the following code to the IPrey interface:

int FleeSpeed { get; set; }

Creating an Interface Method
Methods may be created within interfaces. As with properties, the method must not include an access specifier or a code block. Otherwise, the declaration uses the same syntax as a standard method.
The IPrey interface will include a method called when the animal attempts to escape from a predator. This method will be named “Flee” and will require no parameters. To create it, add the following code to the interface:

void Flee();

Creating the IPredator Interface
The IPrey interface is now complete. We will also create a second interface to represent predatory animals.
This interface will define a property and a method. The property will hold the attack speed of all animals that implement the IPredator interface.
The interface’s method, “Attack” will be called when the predator wants to attack another creature. This method will accept a single parameter containing the prey animal to be attacked. So that any prey animal may be attacked, the parameter will be of the IPrey type. This use of polymorphism means that an object of any class that implements IPredator will be a valid parameter value.
To create the second interface, create a new interface file named IPredator and add the following code:

interface IPredator
{
int AttackSpeed { get; set; }
void Attack(IPrey prey);
}

Implementing an Interface
Once an interface has been declared, one or more classes may implement it. Each class that implements an interface must make concrete all of the interface members. This is achieved by simply declaring all of the methods, properties, indexers, etc. that have been defined in the interface. In each case, the signature of the item from the interface must be exactly matched within the class implementing it.
To create a class that implements an interface, the syntax is similar to that of inheritance. The new class named is followed by the name of the implemented interface. The two names are separated with a colon character (:). Where a class is also inheriting from a base class, the parent class’ name follows the colon. The implemented interface name is then appended, separated from the base class name using a comma.
In our example, we will create a class for cats. The class will implement the IPredator interface. To create the class, add a new class file to the project and name it “Cat”. Modify the class definition to use the interface as follows:

class Cat : IPredator
{
}

As the Cat class does not implement all of the members of the IPredator interface, the code is not currently valid. Attempts to compile the program will produce two errors highlighting the missing method and property.

Implementing Interface Members
Members of implemented interfaces can be declared in two manners. The first is known as implicit implementation. This simply means that each interface member required is declared in the class using the same signature as in the interface. This is the manner that we shall use for the Cat class.
All members of an interface are publicly accessible. This behavior cannot be modified and must be repeated in the implementing class by explicitly adding the “public” access modifier to all of the declarations.
To implement the interface members, and to create a Cat-specific “Purr” method, modify the code of the class as follows:

class Cat : IPredator
{
private int _attackSpeed;
public int AttackSpeed
{
get
{
return _attackSpeed;
}
set
{
_attackSpeed = value;
}
}
public void Attack(IPrey prey)
{
if (_attackSpeed > prey.FleeSpeed)
Console.WriteLine("Caught prey");
else
Console.WriteLine("Prey escaped");
}
public void Purr()
{
Console.WriteLine("Cat purred");
}
}

Note the type of the Attack method’s parameter. The prey object may be of any class that implements IPrey.
As the FleeSpeed property is part of the IPrey interface, the value can be read and compared to the cat’s attack speed to determine if the feline catches its prey.
A similar class can be created demonstrate the IPrey interface. This class will represent fish. Add a new class file named “Fish” to the project and copy in the following code:

class Fish : IPrey
{
private int _fleeSpeed;
public int FleeSpeed
{
get
{
return _fleeSpeed;
}
set
{
_fleeSpeed = value;
}
}
public void Flee()
{
Console.WriteLine("Fish fleeing");
}
}

Testing the Classes
We can now test the cat and fish classes using the Main method of the program. For this simple test, we will create both a cat and a fish object before making the cat try to attack the fish. Modify the Main method as follows and execute the program to perform the test.

static void Main(string[] args)
{
Cat tabby = new Cat();
tabby.AttackSpeed = 10;
Fish bubbles = new Fish();
bubbles.FleeSpeed = 12;
tabby.Purr();
tabby.Attack(bubbles);
}

/* OUTPUT
Cat purred
Prey escaped
*/

Using polymorphism techniques, it is possible to declare a variable using an interface as its type. Although an interface cannot be instantiated, such a variable can be assigned an object of any type that implements the interface. This means that the previous example can be rewritten as shown below. However, as the interface for predators does not contain the “Purr” method, this becomes unavailable and must be removed.

static void Main(string[] args)
{
IPredator tabby = new Cat();
tabby.AttackSpeed = 10;
IPrey bubbles = new Fish();
bubbles.FleeSpeed = 12;
tabby.Attack(bubbles);
}

Implementing Multiple Interfaces
Earlier in the article I mentioned that a single class can implement more than one interface. This provides even more flexibility and opportunities for polymorphism, as instantiated objects of such a class can behave in many different ways according to the interface in use at any given time.
To declare a class that implements more than one interface, the list of interfaces is appended to the class declaration. The list is comma-separated and is preceded by a colon (:). If the class is also inheriting from a base class, the interface list must appear after the name of the parent class.
In our example, we have declared a class for fish and implemented the IPrey interface. Of course, fish can be predators too so we can sensibly implement the IPredator interface for this class. To add the interface to the Fish class, modify the declaration for the class as follows:

class Fish : IPrey, IPredator

Now that the Fish class is to implement the IPredator interface, the relevant members must be declared before the class will compile. Add the following property and method to the class:

private int _attackSpeed;
public int AttackSpeed
{
get
{
return _attackSpeed;
}
set
{
_attackSpeed = value;
}
}
public void Attack(IPrey prey)
{
if (_attackSpeed > prey.FleeSpeed)
Console.WriteLine("Caught prey");
else
Console.WriteLine("Prey escaped");
}

We can now modify the Main method of the program to test the use of a fish as both predator and prey. Note the use of polymorphism of the Fish class as it acts as both an IPredator object for the attacker and an IPrey object for the intended prey parameter.

static void Main(string[] args)
{
IPredator shark = new Fish();
shark.AttackSpeed = 30;
IPrey ray = new Fish();
ray.FleeSpeed = 15;
shark.Attack(ray);
}

/* OUTPUT
Caught prey
*/

Explicit Interface Implementation
In the examples above, all interface members have been implemented in the Cat and Fish classes using implicit implementation. This method requires that public members are created and appear as part of the public interface of the class. Another manner in which interfaces can be realized is known as explicit implementation.
When using explicit implementation, the fully qualified name of each interface member is used in the class definition. This means that both the member name and the interface name are included in each declaration, separated by a full stop, or period. We can demonstrate explicit implementation by modifying the Cat class’ IPredator method and property as follows. Note the use of the IPredator prefixes for the two interface members and that the “public” keyword has been removed.

int IPredator.AttackSpeed
{
get
{
return _attackSpeed;
}
set
{
_attackSpeed = value;
}
}
void IPredator.Attack(IPrey prey)
{
if (_attackSpeed > prey.FleeSpeed)
Console.WriteLine("Caught prey");
else
Console.WriteLine("Prey escaped");
}

One of the key benefits of explicit implementation is seen when a class implements multiple interfaces. If several interfaces included a matching member declaration, this would lead to ambiguity in a class using implicit implementation. As the explicit syntax names the interface being inherited, the ambiguity is removed.
Explicitly implemented members become partially private. In the Cat example, if a Cat object is created the interface members are not available. Only if a Cat object is seen within an IPredator variable do the property and method become available. The following code is therefore invalid:

Cat c = new Cat();
c.AttackSpeed = 30;

Finally, as the members are private within the Cat class, they are not available for inheritance to subclasses.
This means that is not valid to mark such an item as either virtual or abstract.

Interface Inheritance
The last topic of discussion for interfaces is the concept of inheritance. As classes can inherit functionality from a base class, so interfaces can inherit from other interfaces. When one interface inherits from another, the members of the parent interface do not need to be repeated in the child’s code. However, all of the members from both interfaces must be included in a class that implements the child interface. These can be implemented either implicitly or explicitly.
Interface inheritance uses the concept of name hiding. As with classes, if a member is created in a parent interface and duplicated in a child interface the child’s version must use the “new” keyword to hide the parent interface’s version.
To demonstrate interface inheritance we will create a new interface for all animals. IPrey and IPredator will be adjusted so that they inherit from this new, “IAnimal” interface. To begin, add a new interface file named “IAnimal”. Add a single property to the interface to hold the animal’s name.

interface IAnimal
{
string Name { get; set; }
}

To indicate that the IPrey and IPredator interfaces are children of IAnimal, adjust the declarations for the two interfaces as follows:

// IPrey.cs
interface IPrey : IAnimal
{
...
}
// IPredator.cs
interface IPredator : IAnimal
{
...
}

Now that the interfaces inherit from IAnimal, the Cat and Fish classes must also implement IAnimal’s members before the program can be compiled. To declare the property implicitly, add the following code to both classes:

private string _name;
public string Name
{
get
{
return _name;
}
set
{
_name = value;
}
}

The choice of data type for animal variables is now interesting. Both the Cat and Fish classes can be instantiated and assigned to IAnimal or IPredator variables. If used as an IAnimal object, only the Name property will be present. If used as an IPredator object, the members from the IAnimal and IPredator interfaces are available but other members of the class are invisible.
The following code shows the full extent of the polymorphism provided by a Fish object. Note that the object can be assigned to variables of any of the interface types that Fish implements:

Fish bubbles = new Fish();
IAnimal animal = bubbles;
IPredator predator = bubbles;
IPrey prey = bubbles;

Tagged , , . Bookmark the permalink.

One Response to C# Interfaces

  1. Cobracus says:

    Your examples are trivial. To understand interfaces, you must have the definitions separately compilable from implementations. Otherwise there is no point in having interfaces. The definition sits in the calling class – the class that needs a service. The implementation sits in the class providing the service. Think about it.

Leave a Reply

Your email address will not be published. Required fields are marked *


+ 3 = seven

You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code class="" title="" data-url=""> <del datetime=""> <em> <i> <q cite=""> <strike> <strong> <pre class="" title="" data-url=""> <span class="" title="" data-url="">