returning a generic IEnumerable<T>

I'm messing around with generics and IEnumerable abit, but i'm kindof stuck. Here's what i'm trying to do: I want to have a method that returns any collection type - that implements IEnumerable (?) - (so e.g: List, Stack, Queue, ...)

furthermore, i want to be able to return any collection type, of any datatype. so i want this method to be able to return a List<string>, as well as a Stack<int>, as well as a List<double>... etc etc.

 public IEnumerable<T> returnSomething() 
    {
        Stack<int> stackOfInts = new Stack<int>();
        List<string> listOfStrings = new List<string>();
        return stackOfInts;
    }

this is what i've tried so far. this however doesn't work, i get this error:

Cannot implicitly convert type 'System.Collections.Generic.Stack<int>' to 'System.Collections.Generic.IEnumerable<T>'. An explicit conversion exists (are you missing a cast?)

however, if i replace the IEnumerable<T> in the method signature to IEnumerable<int> , i can return any collection of type int. This however means, that now i can't return the ListOfStrings anymore.

would appreciate any suggestions or ideas :)

Answers


You need to add a generic type parameter to your method:

public IEnumerable<T> ReturnSomething<T>() 
{
    Stack<T> stackOfT = new Stack<T>();
    return stackOfT;
}

The type parameter appears after the method name, but before the parameters. It is also possible to have a method with more than one type parameter.

When you call the method you can specify the type:

IEnumerable<int> myInts = ReturnSomething<int>();

The trick is to declare <T> right, if you define generic <T>, then you have to stick to it in your methods, so if you have IEnumerable<T> then elsewhere in your method you must use <T> and not <int> or any other type.

It is only latter when you actually use you generic type you substitute generic <T> for a real type.

See a sample

class Foo<T>
{
    public IEnumerable<T> GetList()
    {
        return new List<T>();
    }

    public IEnumerable<T> GetStack()
    {
        return new Stack<T>();
    }
}

class Program
{
    static void Main(string[] args)
    {
        Foo<int> foo = new Foo<int>();
        IEnumerable<int> list = foo.GetList();
        IEnumerable<int> stack = foo.GetStack();

        Foo<string> foo1 = new Foo<string>();
        IEnumerable<string> list1 = foo1.GetList();
        IEnumerable<string> stack1 = foo1.GetStack();
    }
}

public IEnumerable<T> returnSomething() 
{
    Stack<int> stackOfInts = new Stack<int>();
    return (IEnumerable<T>) stackOfInts;
}

The type parameter needs to be specified by the caller somewhere.

Either when instantiating a generic class:

public class MyClass<T>
{
    public IEnumerable<T> returnSomething()
    {
        Stack<T> stackOfTs = new Stack<T>();
        List<T> listOfTs = new List<T>();
        return stackOfTs;
    }
}

var v = new MyClass<int>();
foreach(var item in v.returnSomething())
{
}

Or when calling a generic method of a non-generic class:

public class MyClass
{
    public IEnumerable<T> returnSomething<T>()
    {
        Stack<T> stackOfTs = new Stack<T>();
        List<T> listOfTs = new List<T>();
        return stackOfTs;
    } 
}


var v = new MyClass();
foreach(var item in v.returnSomething<int>())
{
}

Yes you can return any type if you change IEnumerable<T> to IEnumerable<dynamic>

like this:

public IEnumerable<dynamic> returnSomething() 
{
.....

Need Your Help

Execute stored procedure with an Output parameter?

sql-server stored-procedures

I have a stored procedure that I am trying to test. I am trying to test it through SQL Management Studio. In order to run this test I enter ...

No creation of a WPF window in a DLL project?

wpf dll window

Is there a reason why Visual Studio won't let me create a WPF window in a DLL project?