C#实现KMP算法,在长字符串中找到第一个符合要求的子字符串

KMP算法可以查找符合要求的字符串的索引。

在下面的代码中会打印出方法所消耗的时间。

一些异常的处理:

  1. 比如当word比longwrod还要长的时候异常处理
  2. longwrod或者word为空的时候异常处理
  3. 当word在longwrod中不存在的时候异常处理
csharp 复制代码
       static void Main(string[] args)
        {
            string longwrod = "112312er3338bluifaehilf";
            string word = "3338";
            DateTime beforDT = System.DateTime.Now;
            TMPFunc(longwrod, word);
            DateTime afterDT = System.DateTime.Now;
            TimeSpan ts = afterDT.Subtract(beforDT);
            Console.WriteLine("DateTime总共花费{0}ms.", ts.TotalMilliseconds);
		
        }

        /// <summary>
        /// TMP算法_查找符合要求的字符串的索引
        /// </summary>
        /// <param name="longWord"> 长串</param>
        /// <param name="word">字串</param>
        public static void TMPFunc(string longWord, string word)
        {
            if (string.IsNullOrEmpty(longWord) || string.IsNullOrEmpty(word))
            {
                Console.WriteLine("长字符串和查找字符串不能为空。");
                return;
            }

            if (word.Length > longWord.Length)
            {
                Console.WriteLine("查找字符串长度大于长字符串长度,无法匹配。");
                return;
            }

            int[] prefixTable = CalculatePrefixTable(word);
            int longWordIndex = 0;
            int wordIndex = 0;

            while (longWordIndex < longWord.Length)
            {
                if (longWord[longWordIndex] == word[wordIndex])
                {
                    longWordIndex++;
                    wordIndex++;

                    if (wordIndex == word.Length)
                    {
                        // 找到了匹配
                        Console.WriteLine("匹配找到在索引 " + (longWordIndex - wordIndex));
                        wordIndex = prefixTable[wordIndex - 1];
                    }
                }
                else
                {
                    if (wordIndex != 0)
                    {
                        wordIndex = prefixTable[wordIndex - 1];
                    }
                    else
                    {
                        longWordIndex++;
                    }
                }
            }

            if (wordIndex == 0)
            {
                Console.WriteLine("未找到匹配。");
            }
        }

        private static int[] CalculatePrefixTable(string word)
        {
            int[] prefixTable = new int[word.Length];
            int prefixLength = 0;
            int i = 1;

            while (i < word.Length)
            {
                if (word[i] == word[prefixLength])
                {
                    prefixLength++;
                    prefixTable[i] = prefixLength;
                    i++;
                }
                else
                {
                    if (prefixLength != 0)
                    {
                        prefixLength = prefixTable[prefixLength - 1];
                    }
                    else
                    {
                        prefixTable[i] = 0;
                        i++;
                    }
                }
            }

            return prefixTable;
        }
相关推荐
DolphinDB3 分钟前
DolphinDB 回测插件快速上手
算法
利刃大大20 分钟前
【动态规划:路径问题】最小路径和 && 地下城游戏
算法·动态规划·cpp·路径问题
武大打工仔36 分钟前
用 Java 复现哲学家就餐问题
算法
要做朋鱼燕38 分钟前
【数据结构】用堆解决TOPK问题
数据结构·算法
忒可君40 分钟前
C# winform FTP功能
开发语言·windows·c#
秋难降2 小时前
LRU缓存算法(最近最少使用算法)——工业界缓存淘汰策略的 “默认选择”
数据结构·python·算法
时光追逐者2 小时前
C#/.NET/.NET Core技术前沿周刊 | 第 50 期(2025年8.11-8.17)
c#·.net·.netcore·.net core
CoovallyAIHub3 小时前
线性复杂度破局!Swin Transformer 移位窗口颠覆高分辨率视觉建模
深度学习·算法·计算机视觉
一个会的不多的人3 小时前
C# NX二次开发:操作按钮控件Button和标签控件Label详解
开发语言·c#