在 C# 中用于类型安全树实现(类型安全节点)

in c# for type safe tree implementation (typesafe node)

我正在寻找 /tring 以在 C# 中实现类型安全树实现。

如何在不使用接口(强制在所有地方重新实现树功能)和不使用强制转换的情况下实现类型安全的树?

我有使用树作为公共基础的想法 class,但是类型安全性消失了。我目前的方法是使用泛型。但是我缺少一些返回到基本类型的转换。

下面是一个 reduced/nonworking 示例。 这个想法是返回的节点支持树函数,同时它们也支持它们的基本类型行为。 我可以在没有 Node 的情况下使用下面的 class 并从 Node 继承,但是一方面我失去了类型安全性,并且在继承方面也遇到了问题,因为 Nodes 已经有父级 classes.

我也玩过 class 扩展,但我没有找到任何接近可能的解决方案的东西。

我想我需要一个关于如何继续的小提示。在此先感谢您。

public class Node<T>  // .
{
    public Node<T> parent;
    public List<Node<T>> children;

    protected Node()
    {
        children = new List<Node<T>>();
        parent = null;
    }
    protected Node(Node<T> parent)
        : this()
    {

        this.parent = parent;
        parent.addChildren(this);
    }


    protected void addChildren(Node<T> child)
    {
        children.Add(child);
    }
    public Node<T> getRoot() // returns root node
    public List<Node<T>> flatten()  // return 1d-list of all nodes.

}

I have the idea of using tree as common base class, but then type safety is gone. My current approach is usage generics. But I am missing some conversion back to the base type.

然后将泛型类型约束为您的基类型:

public class Node<T> where T: BaseType { ... }

现在您可以创建任何 Node<MyDerivedType> 类型的树,只要 MyDerivedType 派生自 BaseType

另一方面,我会考虑在您的实施中修改以下内容:

  1. Children 应该是 属性,不要公开字段,除非它是只读的。此外,您不应将其公开为 List;这将使任何人都可以直接添加或删除节点,这可能会违反您的实现中假设的不变量。 Return 改为 IEnumerable<T>

    private readonly List<T> children;
    public IEnumerable<T> Children => children.Select(c => c);
    

    您可以直接 return children 因为它可以隐式转换为 IEnumerable<T>;问题是任何人都可以简单地将其转换回 List<T> 并进行修改。投影它可以保护您免受这种转换。

  2. Flatten 也是如此(顺便说一句,第一个 f 应该大写)。也考虑 returning 一个 IEnumerable<T>

这是一个类型安全的树实现:

public class Tree<T> : List<Tree<T>>
{
    public T Value { get; set; }
}

是的,就是这样。简单。

当然,您可以添加一两个构造函数,并将 Value 属性 设置为只读以使其对 OOP 更加友好。您可以轻松添加 Parent 属性.