使用列表的 C# 递归编程

标签 c# class recursive-datastructures

我正在开发一个程序,其中每个项目都可以保存一个项目数组(我正在制作一个菜单,它具有树状结构)

目前,我将项目作为列表而不是数组,但我不觉得我正在充分利用它来简化代码。我选择了列表而不是标准数组,因为接口(interface)(.add、.remove 等)很有意义。

我有代码来搜索结构并返回名称的路径(即 Item.subitem.subsubitem.subsubsubitem)。下面是我的代码:

public class Item
{
                                                                //public Item[] subitem; <-- Array of Items
    public List<Item> subitem;                                  // <-- List of Items

    public Color itemColor = Color.FromArgb(50,50,200);
    public Rectangle itemSize = new Rectangle(0,0,64,64);
    public Bitmap itemBitmap = null;
    public string itemName;


    public string LocateItem(string searchName)
    {
        string tItemName = null;

        //if the item name matches the search parameter, send it up)
        if (itemName == searchName)
        {
            return itemName;
        }

        if (subitem != null)
        {

            //spiral down a level
            foreach (Item tSearchItem in subitem)
            {
                tItemName = tSearchItem.LocateItem(searchName);

                if (tItemName != null)
                    break;  //exit for if item was found
            }
        }


        //do name logic (use index numbers)
        //if LocateItem of the subitems returned nothing and the current item is not a match, return null (not found)
        if (tItemName == null && itemName != searchName)
        {
            return null;
        }

        //if it's not the item being searched for and the search item was found, change the string and return it up
        if (tItemName != null && itemName != searchName)
        {
            tItemName.Insert(0, itemName + ".");  //insert the parent name on the left -->  TopItem.SubItem.SubSubItem.SubSubSubItem
            return tItemName;
        }

        //default not found
        return null;
    }


}

我的问题是是否有更简单的方法来使用列表来做到这一点?我一直在脑子里反复思考是否应该使用列表还是仅使用数组。我有一个列表的唯一原因是这样我就不必在每次添加或删除项目时编写代码来调整数组的大小。

最佳答案

列表听起来很棒。不过,我建议对您的定义进行变体。尝试像这样创建你的类:

public class Item : List<Item>
{
    public string Name;
}

如果你做Item继承自List<Item>你会自动将其变成一棵树,而不需要 subitem字段。

这是我的类(class)的完整版本:

public class Item : List<Item>
{
    public string Name;

    private List<Item> LocateItems(string searchName)
    {
        if (this.Name == searchName)
            return (new [] { this }).ToList();

        var result =
            this
                .Select(s => s.LocateItems(searchName))
                .Where(x => x !=null && x.Count > 0)
                .FirstOrDefault();

        if (result != null)
            result.Add(this);

        return result;
    }

    public string LocateItem(string searchName)
    {
        var items = this.LocateItems(searchName);
        if (items == null)
            return null;
        else
            return String.Join(".", items.Select(i => i.Name).Reverse());
    }
}

方法LocateItems返回 Item 的列表从 Item 开始匹配并跟随所有父项 Item实例直至并包括根。

我用这段代码进行了测试:

var foos = new Item() { Name = "Foo" };
var bars = new Item() { Name = "Bar" };
var qazs = new Item() { Name = "Qaz" };
var wees = new Item() { Name = "Wee" };

foos.Add(bars);
bars.Add(qazs);
foos.Add(wees);

Console.WriteLine(foos.LocateItem("Wee"));
Console.WriteLine(foos.LocateItem("Qaz"));
Console.WriteLine(foos.LocateItem("Bar"));
Console.WriteLine(foos.LocateItem("Foo"));

我得到了这些结果:

Foo.Wee
Foo.Bar.Qaz
Foo.Bar
Foo

关于使用列表的 C# 递归编程,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/12241540/

相关文章:

c# - azure blob 存储出现错误 - 指定的资源不存在

c# - 日期的正则表达式不起作用; MVC3 数据注解

Python - 静态类变量

c# - 检查对象是否与给定列表中的任何类型匹配的替代方法

python - 如何找到列表中返回到前一个零的差值?

c++ - 多维数组中的 Operator[] 重载 C++

Python-从字典列表创建动态嵌套字典

c# - 套接字行为 - 乱序写入的数据

c# - 这个自定义比较功能有什么问题

javascript - 既然 javascript 有原生 'classes",模块模式仍然是必要的