C# 递归类的最佳实践

C# 递归类的最佳实践,c#,class,recursion,self-reference,dice,C#,Class,Recursion,Self Reference,Dice,问题: 我想为自定义的dice构建一个类。但它还应提供以下内容: 每个边可以包含另一个骰子 侧面的数量应可动态扩展,但必须至少包含一个侧面 逻辑上,dice需要有一个currentSide 每个侧都有一个属性,该属性提供该侧的内容(在D6上,它将是“4”) 到目前为止还不错,我去做了两个类dice和side,并给了他们我认为他们需要的属性 public class Side { //public bool HasDice { get { return Dice != null; }

问题:

我想为自定义的
dice
构建一个类。但它还应提供以下内容:

  • 每个
    可以包含另一个
    骰子
  • 侧面的数量应可动态扩展,但必须至少包含一个侧面
    
    • 逻辑上,
      dice
      需要有一个
      currentSide
  • 每个
    都有一个
    属性
    ,该属性提供该侧的内容(在D6上,它将是
    “4”
  • 到目前为止还不错,我去做了两个类
    dice
    side
    ,并给了他们我认为他们需要的属性

    public class Side
    {
        //public bool HasDice { get { return Dice != null; } } - Removed not needed
        public Dice Dice { get; set; }
        public string Value { get; set; }
    }
    
    public class Dice
    {
        public ObservableCollection<Side> Sides { get; set; }
        public string Name { get; set; }
        public Side CurrentSide { get; set; }
    }
    
    我应该在构建对象时检查此选项吗

    编辑:

    • 如果D1滚动S2,则不应滚动D2。另外
      D2.Dice=Null

    • 如果D1轧制S1,则应轧制D2

    • 如果D2轧制S1,则应轧制D3

    • 如果D2轧制S2,则应轧制D4

    D3和D4不应该触发任何掷骰。

    根据您所说的,我建议您创建一个骰子的对象图,其中一个骰子连接到其他骰子,然后运行拓扑排序算法以显示循环依赖关系

    要做到这一点,我建议你要么自己写,要么使用这个工具

    现在,我自己曾经使用过它,并为
    IEnumerable
    编写了一个扩展,它返回排序的
    IList
    ,在某种程度上,第一个返回的项是其他项从未引用过的项。后者是最受参考的。(或者相反)在循环依赖的情况下,抛出异常。我的扩展使用QuickGraph库

    public static IList<T> OrderTopologically<T>(this IEnumerable<T> e, Func<T, IEnumerable<T>> dependenciesSelector)
    {
        var graph = new AdjacencyGraph<T, Edge<T>>();
    
        foreach (T item in e)
        {
            graph.AddVertex(item);
    
            foreach (T dependecy in dependenciesSelector(item))
            {
                graph.AddEdge(new Edge<T>(item, dependecy));
            }
        }
    
        var topSort = new TopologicalSortAlgorithm<T, Edge<T>>(graph);
    
        try
        {
            topSort.Compute();
        }
        catch (NonAcyclicGraphException cyclicException)
        {
            throw new ElQueueException("Circular reference detected while processing javascript dependency order.", cyclicException);
        }
        catch (KeyNotFoundException keyNotFoundException)
        {
            throw new ElQueueException("Dependency could not be found.", keyNotFoundException);
        }
    
        return topSort.SortedVertices;
    }
    
    公共静态IList OrderTopology(此IEnumerable e,Func dependenciesSelector)
    {
    变量图=新的邻接图();
    foreach(e中的T项)
    {
    图.添加顶点(项);
    foreach(依赖项选择器(项目)中的T依赖项)
    {
    图.增边(新边(项,依赖项));
    }
    }
    var topSort=新拓扑排序算法(图);
    尝试
    {
    topSort.Compute();
    }
    捕获(非周期性图形异常周期性异常)
    {
    抛出新的ElQueueException(“在处理javascript依赖项顺序时检测到循环引用。”,cycliceException);
    }
    捕获(KeyNotFoundException KeyNotFoundException)
    {
    抛出新的ElQueueException(“找不到依赖项。”,keyNotFoundException);
    }
    返回topSort.SortedAdverties;
    }
    
    你所做的被称为一个。您的程序(“机器”)始终处于某种状态,但执行某些操作后可能会改变状态。根据逻辑,机器可以多次处于相同状态是可以接受的。所以,我不会太在意机器逻辑中的循环。如果用户想要循环,那么就让他拥有它,只要机器能够达到某种最终状态,程序达到执行结束。

    除了良好的编程实践之外,谁提出了这种设计?公共财产说如果一方有骰子?这对你有什么意义吗?
    侧的
    骰子
    参考是指该侧所属的骰子,还是在其他骰子上有骰子?可能是超级骰子,因此每侧都有另一个骰子@NielsKeurentjes这是如此非专业的好+1。因此
    方面。骰子
    可以选择性地引用任何
    骰子
    ,除了它包含的那一个吗?我更新了我的帖子,上面有一个关于我希望骰子如何表现的图像,这可以通过对象图实现吗?如果是的话,我会读更多的内容。:)
    public static IList<T> OrderTopologically<T>(this IEnumerable<T> e, Func<T, IEnumerable<T>> dependenciesSelector)
    {
        var graph = new AdjacencyGraph<T, Edge<T>>();
    
        foreach (T item in e)
        {
            graph.AddVertex(item);
    
            foreach (T dependecy in dependenciesSelector(item))
            {
                graph.AddEdge(new Edge<T>(item, dependecy));
            }
        }
    
        var topSort = new TopologicalSortAlgorithm<T, Edge<T>>(graph);
    
        try
        {
            topSort.Compute();
        }
        catch (NonAcyclicGraphException cyclicException)
        {
            throw new ElQueueException("Circular reference detected while processing javascript dependency order.", cyclicException);
        }
        catch (KeyNotFoundException keyNotFoundException)
        {
            throw new ElQueueException("Dependency could not be found.", keyNotFoundException);
        }
    
        return topSort.SortedVertices;
    }