Click here to Skip to main content
14,830,755 members
Please Sign up or sign in to vote.
3.20/5 (2 votes)
See more:
I am very green when it comes to generics.

Can I convert a function like this to a generic one, and if so can someone give me an example implementation of it?

C#
public Dictionary<Sheet, bool> DeleteSheets(List<Sheet> sheets)
        {
            Dictionary<Sheet, bool> results = new Dictionary<Sheet, bool>();
            foreach (Sheet s in sheets)
                results.Add(s, DeleteSheet(s));

            return results;
        }


I have several functions just like this, except the return value, method parameter, and the method called in the .Add function are different types.

Like I said, I am green when it comes to this....

Thanks!
Posted
Comments
BillWoodruff 20-Dec-13 11:37am
   
This is a recursive function: a new Dictionary<Sheet, bool> is declared every time it is evaluated.

Is a 'Sheet a List<Sheet> ? I think to respond helpfully we really need to know the structure of 'Sheet.

Try:
C#
public Dictionary<T, bool> DeleteSheets<T>(List<T> data)
    {
    Dictionary<T, bool> results = new Dictionary<T, bool>();
    foreach (T s in data)
        results.Add(s, Delete<T>(s));

    return results;
    }
public bool Delete<T>(T s) { return true; }


Griff,

The Delete method executes different code, based on what function it is, but they all return bools. How can I handle that? Use a delegate for this?


That's not as simple as it sounds: you can use a Delegate:
C#
Dictionary<string, bool> data = DeleteSheets(new List<string>() { "hello", "goodbye" }, DeleteString);
    Dictionary<int, bool> data2 = DeleteSheets(new List<int>() { 1, 2, 3 }, DeleteString);
    }

bool DeleteString(string s) { Console.WriteLine(s); return true; }
bool DeleteString(int s) { Console.WriteLine("Del" + s ); return true; }
public delegate bool DeleteMethod<T>(T t);
public Dictionary<T, bool> DeleteSheets<T>(List<T> data, DeleteMethod<T> delete ) //where T: Base
    {
    Dictionary<T, bool> results = new Dictionary<T, bool>();
    foreach (T s in data)
        results.Add(s, delete(s));

    return results;
    }

And it will call the appropriate method.

But I'd rather restrict the generic to a base class and do it via overloading instead:
C#
Dictionary<Base, bool> data2 = DeleteSheets(new List<Base>() { new A(), new A(), new B() });
    }

public Dictionary<T, bool> DeleteSheets<T>(List<T> data ) where T: Base
    {
    Dictionary<T, bool> results = new Dictionary<T, bool>();
    foreach (T s in data)
        results.Add(s, s.Delete());

    return results;
    }
public abstract class Base
    {
    public abstract bool Delete();
    }
public class A : Base
    {
    public override bool Delete()
        {
        Console.WriteLine("A Delete");
        return true;
        }
    }
public class B : Base
    {
    public override bool Delete()
        {
        Console.WriteLine("B Delete");
        return true;
        }
    }


It just seems like a "cleaner" solution.
   
v2
Comments
David Knechtges 20-Dec-13 11:28am
   
Griff,

The Delete method executes different code, based on what function it is, but they all return bools. How can I handle that? Use a delegate for this?
bowlturner 20-Dec-13 11:37am
   
In my solution I added in sending in the function to run..
OriginalGriff 20-Dec-13 11:55am
   
Answer updated.
bowlturner 20-Dec-13 12:07pm
   
I like it, but you'll get an exception if someone sends a list that doesn't have the delete method on it's object.
OriginalGriff 20-Dec-13 12:14pm
   
That's why I prefer the base class version: the derived classes have to implement the method so all the checking is compile time.
bowlturner 20-Dec-13 12:30pm
   
right! I didn't look close enough the first time.
This should be close to what you are looking for. Not sure what the DeleteSheets() in the foreach is supposed to do. If I did I might be able to help there too.

Made changes to take the DeleteSheet func as a parameter.

C#
public Dictionary<T, bool> DeleteSheets<T>(List<T> sheets, Func<T, bool> delT)
       {
           Dictionary<T, bool> results = new Dictionary<T, bool>();
           foreach (T s in sheets)
               results.Add(s, delT(s));

           return results;
       }
   
v2
Comments
David Knechtges 20-Dec-13 11:37am
   
DeleteSheet represents a method that is called. They all have different functionality, but all return a bool. Should I use a delegate for this and pass the delegate to the generic method?
bowlturner 20-Dec-13 11:43am
   
I changed it to take a delegate, it takes a <t> and returns a bool
David Knechtges 20-Dec-13 11:41am
   
That worked perfectly for me.... Thank you very much!
bowlturner 20-Dec-13 11:44am
   
your welcome.
Just replace the type you want to be generic with a letter (the convention is T):
C#
public Dictionary<T, bool> DeleteSheets(List<T> sheets)
        {
            Dictionary<T, bool> results = new Dictionary<T, bool>();
            foreach (T s in sheets)
                results.Add(s, DeleteSheet(s));

            return results;
        }
   

This content, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)




CodeProject, 20 Bay Street, 11th Floor Toronto, Ontario, Canada M5J 2N8 +1 (416) 849-8900