Pages
Calender
<<  September 2010  >>
MoTuWeThFrSaSu
303112345
6789101112
13141516171819
20212223242526
27282930123
45678910
Blogroll
    ajander singh , Created On 1. April 2010, 19:04

    An interface contains only the signatures of methods,  events, indexers or properties. When a class or struct implements the interface then that class/struct must implement the members of the interface that are specified in the interface definition.

    interface IEquatable<T> 
    {
         bool Equals(T obj); 
    }

    An interface cannot contain fields and members are automatically public in interface as well and an interface can inherit from one or more base interfaces. When a base type list contains a base class and interfaces, the base class must come first in the list.

    A class that implements an interface can explicitly implement members of that interface. An explicitly implemented member cannot be accessed through a class instance, but only through an instance of the interface.

    Interfaces can inherit other interfaces. It is possible for a class to inherit an interface multiple times, through base classes or interfaces it inherits. In this case, the class can only implement the interface one time, if it is declared as part of the new class. If the inherited interface is not declared as part of the new class, its implementation is provided by the base class that declared it. It is possible for a base class to implement interface members using virtual members; in that case, the class inheriting the interface can change the interface behavior by overriding the virtual members.

    it was necessary to incorporate some other method so that the class can inherit the behavior of more than one class, avoiding the problem of name ambiguity that is found in C++. With name ambiguity, the object of a class does not know which method to call if the two base classes of that class object contain the same named method.


    Interfaces Overview

    An interface has the following properties:

    •       An interface is like an abstract base class: any non-abstract type inheriting the interface must implement all its members.
    •       An interface cannot be instantiated directly.
    •       Interfaces can contain events, indexers, methods and properties.
    •       Interfaces contain no implementation of methods.
    •       Classes and structs can inherit from more than one interface.
    •       An interface can itself inherit from multiple interfaces.



    Both delegates and interfaces allow a class designer to separate type declarations and implementation. A given interface can be inherited and implemented by any class or struct; a delegate can created for a method on any class, as long as the method fits the method signature for the delegate. An interface reference or a delegate can be used by an object with no knowledge of the class that implements the interface or delegate method. Given these similarities, when should a class designer use a delegate and when should they use an interface?

    Use a delegate when:

    • An eventing design pattern is used.

    • It is desirable to encapsulate a static method.

    • The caller has no need access other properties, methods, or interfaces on the object implementing the method.

    • Easy composition is desired.

    • A class may need more than one implementation of the method.

    Use an interface when:

    • There are a group of related methods that may be called.

    • A class only needs one implementation of the method.

    • The class using the interface will want to cast that interface to other interface or class types.

    • The method being implemented is linked to the type or identity of the class: for example, comparison methods.

    One good example of using a single-method interface instead of a delegate is IComparable or IComparable. IComparable declares the CompareTo method, which returns an integer specifying a less than, equal to, or greater than relationship between two objects of the same type. IComparable can be used as the basis of a sort algorithm, and while using a delegate comparison method as the basis of a sort algorithm would be valid, it is not ideal. Because the ability to compare belongs to the class, and the comparison algorithm doesn’t change at run-time, a single-method interface is ideal.

     

    Extracted from Microsoft Technet articles.



    Ajander Singh , Created On 7. March 2009, 20:29

    As you know, a variable of a value type can never be null; it always contains the value type's value itself. In fact, this is why they call value types value types. Unfortunately, there are some scenarios in which this is a problem.

    Examples:

    Case 1: When designing a database, it's possible to define a column's data type to be a 32-bit integer that would map to the FCL's Int32 data type. But a column in a database can indicate that the value is nullable. That is, it is OK to have no value in the row's column. Working with database data by using the Microsoft .NET Framework can be quite difficult because in the common language runtime (CLR), thereis no way to represent an Int32 value as null.

    Case 2:  In Java, the java.util.Date class is a reference type, and therefore, a variable of this type can be set to null. However, in the CLR, a System.DateTime is a value type, and a DateTime variable can never be null. If an application written in Java wants  to communicate a date/time to a Web service running the CLR, there is a problem if the Java application sends null because the CLR has no way to represent this and operate on it.

    To improve this situation, Microsoft added the concept of nullable value types to the CLR. To understand how they work, we first need to look at the System.Nullable<T> class, which is defined in the FCL. Here is the logical representation of how the System.Nullable<T> type is defined:

     using System;
    namespace System
    {
        using System.Globalization;
        using System.Reflection;
        using System.Collections.Generic;
        using System.Runtime.CompilerServices;
        using System.Security;

        // Warning, don't put System.Runtime.Serialization.On*Serializ*Attribute
        // on this class without first fixing ObjectClone::InvokeVtsCallbacks
        // Also, because we have special type system support that says a a boxed Nullable<T>
        // can be used where a boxed<T> is use, Nullable<T> can not implement any intefaces
        // at all (since T may not). Do NOT add any interfaces to Nullable!
        //
        [TypeDependencyAttribute("System.Collections.Generic.NullableComparer`1")]
        [TypeDependencyAttribute("System.Collections.Generic.NullableEqualityComparer`1")]
        [Serializable()]
        public struct Nullable<T> where T : struct
        {
            private bool hasValue;
            internal T value;

            public Nullable(T value)
            {
                this.value = value;
                this.hasValue = true;
            }

            public bool HasValue
            {
                get { return hasValue; }
            }

            public T Value
            {
                get
                {
                    if (!HasValue)
                    {
                        ThrowHelper.ThrowInvalidOperationException(ExceptionResource.InvalidOperation_NoValue);
                    }
                    return value;
                }
            }

            public T GetValueOrDefault()
            {
                return value;
            }

            public T GetValueOrDefault(T defaultValue)
            {
                return HasValue ? value : defaultValue;
            }

            public override bool Equals(object other)
            {
                if (!HasValue)
                    return other == null;
                if (other == null)
                    return false;
                return value.Equals(other);
            }

            public override int GetHashCode()
            {
                return HasValue ? value.GetHashCode() : 0;
            }

            public override string ToString()
            {
                return HasValue ? value.ToString() : "";
            }

            public static implicit operator Nullable<T>(T value)
            {
                return new Nullable<T>(value);
            }

            public static explicit operator T(Nullable<T> value)
            {
                return value.Value;
            }

            // The following already obsoleted methods were removed:
            // public int CompareTo(object other)
            // public int CompareTo(Nullable<T> other)
            // public bool Equals(Nullable<T> other)
            // public static Nullable<T> FromObject(object value)
            // public object ToObject()
            // public string ToString(string format)
            // public string ToString(IFormatProvider provider)
            // public string ToString(string format, IFormatProvider provider)

            // The following newly obsoleted methods were removed:
            // string IFormattable.ToString(string format, IFormatProvider provider)
            // int IComparable.CompareTo(object other)
            // int IComparable<Nullable<T>>.CompareTo(Nullable<T> other)
            // bool IEquatable<Nullable<T>>.Equals(Nullable<T> other)
        }
    }

    As you can see, this class encapsulates the notion of a value type than can also be null. Since Nullable<T>  is itself a value type, instances of it are still fairly lightweight. That is, instances can still be on the stack, and an instance is the same size as the original value type plus the size of a Boolean field. Notice that Nullable's type parameter, T, is constrained to struct. This was done because reference type variables can already be null.

    So now, if you want to use a nullable Int32 in your code, you can write something like this:

    Nullable<Int32> x = 5;
    Nullable<Int32> y = null;
    Console.WriteLine("x: HasValue={0}, Value={1}",
    x.HasValue, x.Value);
    Console.WriteLine("y: HasValue={0} , Value={1}",
    y.HasValue, y.GetValueOrDefault());


    When I compile and run this code, I get the following output:

    x: HasValue=True, Value=5
    y: HasValue=False, Value=0

     

    C#'s Null-Coalescing Operator

    C# has an operator called the null-coalescing operator (??), which takes two operands. If the operand on the left is not null,  the operand's value is returned. If the operand on the left is null,  the value of the right operand is returned. The null-coalescing operator offers a very convenient way to set a variable's default value.

    A cool feature of the null-coalescing operator is that it can be used with reference types as well as nullable value types. Here is some code that demonstrates the use of the null-coalescing operator:

    private static void NullCoalescingOperator() {
        Int32? b = null;
        // The line below is equivalent to:
        // x = (b.HasValue) ? b.Value : 123
        Int32 x = b ?? 123;
        Console.WriteLine(x); // "123"
    }