C# 识别最频繁的模式¿;计算标准?

C# 识别最频繁的模式¿;计算标准?,c#,algorithm,pattern-matching,C#,Algorithm,Pattern Matching,我实际上正在处理一段代码,它将采用一个通用枚举和一个给定的长度,并将返回在指定长度的枚举中找到的最频繁的模式以及它出现的次数 因此,我的方法具有以下特征: public static IEnumerable<T> ExtractFixedLengthPatter<T>(IEnumerable<T> source, int length, out int timesFound) { ... } 我构建此树的方法是迭代流,在每次迭代中,我创建一个自定义迭代器

我实际上正在处理一段代码,它将采用一个通用枚举和一个给定的长度,并将返回在指定长度的枚举中找到的最频繁的模式以及它出现的次数

因此,我的方法具有以下特征:

public static IEnumerable<T> ExtractFixedLengthPatter<T>(IEnumerable<T> source, int length, out int timesFound) { ... }
我构建此树的方法是迭代流,在每次迭代中,我创建一个自定义迭代器,从当前位置获取第一个
长度
项,并填充树:

    1rst outer iteration: {1}
       Fixed length iterator: {1}
                              {2}

    2nd outer iteration: {2}
       Fixed length iterator: {2}
                              {1}
等等

然后,我简单地识别具有最大计数的最后一个节点,并遍历树以获得最频繁的反转模式。我改变了模式,我就完蛋了

这个算法运行得很好,速度也很快。问题是一位同事声称它有一个严重的bug。考虑以下情况:

 111111
很明显,最常见的长度模式
2
11
。问题是,它在枚举中出现了多少次?我的同事声称正确答案是
3

 111111
 11
   11
     11
我的算法返回
5

 111111
 11
  11
   11
    11
     11
哪一个是正确答案?我倾向于相信它的
5
,但如果它的
3
,有没有人看到一种简单的方法,我可以调整或改变算法来识别这种情况?

如果问题是“有多少次
11
出现在
111111
”中,只有一个答案:五次——在索引0、1、2、3和4处

您的同事正在回答一个不同的问题-在
111111
中包含了多少个不重叠的
11
模式副本,这实际上是三个:索引0、2和4

我们需要不重叠的副本,我不知道如何适应现有的算法,我不想浪费编写它所花的时间;它的工作速度快,效率高。也许存储每个节点的索引信息,并执行最终的通过检查索引和模式长度以删除重叠副本

您可以通过最少的修改重用您的算法。保留在每个叶节点上找到匹配项的最后一个元素的索引,以及当前保留的总计数。当您的算法到达叶并准备增加总计数时,它应该检查之前的索引是否至少是从当前索引返回的
n
项。如果超过
n
项,则增加计数;否则,忽略此顺序。

如果问题是“在
111111
中出现多少次
11
”,则只有一个答案:五次-在索引0、1、2、3和4处

您的同事正在回答一个不同的问题-在
111111
中包含了多少个不重叠的
11
模式副本,这实际上是三个:索引0、2和4

我们需要不重叠的副本,我不知道如何适应现有的算法,我不想浪费编写它所花的时间;它的工作速度快,效率高。也许存储每个节点的索引信息,并执行最终的通过检查索引和模式长度以删除重叠副本


您可以通过最少的修改重用您的算法。保留在每个叶节点上找到匹配项的最后一个元素的索引,以及当前保留的总计数。当您的算法到达叶并准备增加总计数时,它应该检查之前的索引是否至少是从当前索引返回的
n
项。如果超过
n
项,则增加计数;否则,忽略此顺序。

如果您必须调整您的方法以使用同事的计数程序,您可以这样做:

  • 添加将用于最终节点的附加字段(除了
    计数
    字段之外),将其命名为
    lastIndex
    ,以存储导致该最终节点的
    计数增加的最后位置
    
  • 每次应增加最后一个节点的
    计数
    ,首先检查它是否与该序列的上一次出现(已知从
    lastIndex
    开始)重叠。情况可能如下所示:


if(node.lastIndex==INVALID_INDEX | | | node.lastIndex+length如果您必须调整您的方法以使用同事的计数过程,您可以这样做:

  • 添加将用于最终节点的附加字段(除了
    计数
    字段之外),将其命名为
    lastIndex
    ,以存储导致该最终节点的
    计数增加的最后位置
  • 每次应增加最后一个节点的
    计数
    ,首先检查它是否与该序列的上一次出现(已知该序列是从
    lastIndex
    开始)重叠。情况可能如下所示:


if(node.lastIndex==无效的| | | node.lastIndex+长度我会说答案是5,但这确实取决于您的使用案例。不过,最终,这个问题似乎与主题无关。
111111
11
的计数是一个惯例问题,决定它是3还是5,重叠模式是否计数。@DavidG及其最终确定正确答案为3?您是否看到一种简单的方法来适应算法的一般方法(显然不需要代码)?我们如何建议如何做到这一点?我们确实需要代码,或者至少需要一个具体的算法。抱歉,但这实际上是离题的。我想说答案是5,但这实际上取决于您的使用案例。不过,最终,这个问题似乎离题了。在
111111
11
的计数是一个有争议的问题n确定它是3还是5,重叠模式是否计数。@DavidG和它的fi
 111111
 11
  11
   11
    11
     11
if (node.lastIndex == INVALID_INDEX || node.lastIndex + length <= iterator.currentIndex()) {
    node.count++;
    node.lastIndex = iterator.currentIndex();
}