views:

419

answers:

2

Hi folks,

I have a class named "baseClass". From this class I inherit a class names "inheritedClass" (public class inheritedClass: baseClass)

The baseClass contains a public function that returns a HashSet<baseClass>. When called from the inheritedClass, the return type is obviously still HashSet<baseClass>, but I need a HashSet<inheritedClass>.

A conversion ala (HashSet<inheritedClass>)returnValue, where returnValue is of Type HashSet<baseClass> doesn't work.

Is there a way to convert the HashSet-Type from baseClass to inheritedClass without converting each element manually?

Thanks in advance, Frank

+1  A: 

Do you really mean C# in the tags? HashMap is a Java type. Also it generally has two type parameters rather than one...

In C#, generic classes are always invariant. Some interfaces will be variant in C# 4, but very few (only those which either only use the type parameter in an output positiion, e.g. IEnumerable<T>, or only use the type parameter in an input position, e.g. IComparable<T>).

If you can provide more precise information about your situation, we'll probably be able to help come up with a simple solution - particularly if you can use LINQ with its Cast<T>() method.

EDIT: Okay, with HashSet<T>:

HashSet<BaseType> baseSet = ...;
var derivedSet = new HashSet<DerivedType>(baseSet.Cast<DerivedType>());

Note that even with C# 4 this would be necessary because the compiler doesn't know that every value in baseSet is an instance of DerivedType - there has to be an execution-time check. The reverse (creating a HashSet<BaseType> from a HashSet<DerivedType>) would work in C# 4.

FURTHER EDIT: If you just want to use UnionWith, that doesn't require a HashSet<DerivedType> - it requires an IEnumerable<DerivedType>. I suggest you do:

HashSet<BaseType> baseSet = ...;
HashSet<DerivedType> derivedSet = ...;

derivedSet.UnionWith(baseSet.Cast<DerivedType>());
Jon Skeet
Arr ... I ment HashSet, not HashMap.From your answer I read, that it is not possible to convert the HashSet-Type and do have to do it manually, right?What is behind the question: I want to use the Union-method of the HashSet<inheritedType>, so I need to provide a Parameter of the Type HashSet<inheritedType>, but my function returns HashSet<baseType>
The UnionWith-method, not Union-method
Ah, using UnionWith is simpler - see my second edit.
Jon Skeet
the Cast<DerivedType>() is what I was looking for, many thanks!
A: 

Here's the solution

//**Your BaseClass**
public class BaseClass<T> where T : BaseClass<T>
{
    public HashSet<T> GetHashSet()
    {
        HashSet<T> _hSet = new HashSet<T>();
        //do some work              
        //create a HashSet<T> and return;              
        return _hSet;
    }
}
//**Your Inherited/Derived Class**
public class InheritedClass : BaseClass<InheritedClass>
{
    //you have the method inherited as you need.}
}
this. __curious_geek
I would suggest adding a where clause to the generic type:where T : BaseClass
Oliver Hanappi
@Oliver: thanks oliver, I added a proper where clause now. It seems ok now ?
this. __curious_geek