harryovers
harryovers

Reputation: 3138

Searching List<Items> then change to List<ItemTypeA : Item>

I have this code and i need to be able to search through different lists of HierarchyItems and return a list of the correct type
i.e. Hierarchy h = new Hierarchy();
//add a load of items of HierarchyItemA type;
List<HierarchyItemA> results = h.Search("text");

CODE:

public class Hierarchy
{
    private List<HierarchyItem> items;

    public Hierarchy()
    {
        items = new List<T>();
    }
    public void AddItem(HierarchyItem item)
    {
        items.Add(item);
    }
    public List<T> Search(string searchText)
    {
        List<T> results = new List<T>();
        foreach (HierarchyItem item in items)
        {
            if (item.DisplayText().ToLower().Contains(searchText.ToLower()))
            {
                results.Add(item);
            }
        }
        return results;
    }
}
public abstract class HierarchyItem
{
    public string DisplayText()
    {
        //returns a string
    }
}
public class HierarchyItemA : HierarchyItem
{
    //do whatever
}
public class HierarchyItemB : HierarchyItem
{
    //do whatever
}

Cheers

EDIT: there are several hierarchies each one only has one type in it. the Hierarchy.Search(text) should return a list containing items of the correct type (correct being of type A or B)

Upvotes: 2

Views: 344

Answers (3)

jason
jason

Reputation: 241641

Okay, I think I understand what you're trying to do now. Thanks for clarifying.

First, you need to declare the class Hierarchy as generic by replacing public class Hierarchy with public class Hierarchy<T>. We'll also put a constraint on it that T must be a HierarchyItem.

public class Hierarchy<T> where T : HierarchyItem

We'll replace private List<HierarchyItem> items with

private List<T> items;

and public void AddItem(HierarchyItem item) with

public void AddItem(T item)

And finally, the line foreach (HierarchyItem item in items) in the method search should be replaced by

foreach(T item in items).

Thus, we end up with

public class Hierarchy<T> where T: HierarchyItem {
    List<T> items;

    public Hierarchy() {
        items = new List<T>();
    }
    public void AddItem(T item) {
        items.Add(item);
    }
    public List<T> Search(string searchText) {
        List<T> results = new List<T>();
        foreach (T item in items) {
            if (item.DisplayText().ToLower().Contains(searchText.ToLower())) {
                results.Add(item);
            }
        }
        return results;
    }
}

And that should be what you're seeking.

Upvotes: 2

Stan R.
Stan R.

Reputation: 16065

I think what you mean is this, however Jason's answer is just as correct.

 public List<T> Search(string searchText) where T : HierarchyItem
    {
        List<T> results = new List<T>();
        foreach (HierarchyItem item in items)
        {
            if (item.DisplayText().ToLower().Contains(searchText.ToLower()))
            {
                 T castedItem = item as T;
                 if(castedItem != null )
                      results.Add(item);
            }
        }

        return results; 
    }

Upvotes: 0

tom.dietrich
tom.dietrich

Reputation: 8347

Wow, way to much code for those other answers. This is a one line problem peeps.

public List<T> Search(string searchText) where T: HirearchyItem
    {
        return Items.OfType<T>().Where(t => t.DisplayText.ToUpper().Contains(searchText.ToUpper())).ToList<T>();   
    }

But if part of the design is that any Hirearchy can only contain items of a single HirearchyItem type, then you may want to make Hirearchy itself a generic class.

Truth be told, Hirearchy is really just a wrapper for a List, why don't you just create an interface for DisplayText and an extention method for List when T implements IHasDisplayText that performs this search?

Upvotes: 0

Related Questions