本文共 1705 字,大约阅读时间需要 5 分钟。
最长公共子序列(Longest Common Subsequence,LCS)是一种经典的动态规划问题,用于找出两个序列中最长的公共子序列。这种算法在编辑距离、多序列比对等领域有广泛应用。
LCS算法的核心思想是通过动态规划将问题分解为更小的子问题。具体来说,假设我们有两个序列 str1 和 str2,我们可以定义一个二维数组 dp[i][j],其中 dp[i][j] 表示 str1 的前 i 个字符与 str2 的前 j 个字符的最长公共子序列的长度。
str1[i-1] == str2[j-1],则说明这两个字符是相同的,因此 dp[i][j] = dp[i-1][j-1] + 1。str1[i-1] != str2[j-1],则说明这两个字符不相同,我们需要从左边或上边的子问题中取最大值,即 dp[i][j] = max(dp[i-1][j], dp[i][j-1])。通过递归关系,我们可以逐步填充 dp 表格,最终 dp[m][n] 就是我们要找的最长公共子序列的长度,其中 m 和 n 分别是两个序列的长度。
#importNSString *longestCommonSubsequence(NSString *str1, NSString *str2) { if (str1 == nil || str2 == nil) { return nil; } const NSInteger gridSize = max(str1.length, str2.length); NSInteger *dp = (NSInteger *)malloc(gridSize * gridSize); for (NSInteger i = 0; i < gridSize; i++) { for (NSInteger j = 0; j < gridSize; j++) { if (str1[i] == str2[j]) { if (i > 0 && j > 0) { dp[i][j] = dp[i-1][j-1] + 1; } else { dp[i][j] = 1; } } else { dp[i][j] = max(dp[i-1][j], dp[i][j-1]); } } } return str1.length == 0 || str2.length == 0 ? @"" : [str1 substringWithRange: dp];}
导入与函数定义
首先导入Foundation 框架,定义一个用于计算最长公共子序列的函数 longestCommonSubsequence。边界条件处理
检查输入字符串是否为nil,如果是,返回 nil;否则继续执行。动态规划表格初始化
创建一个二维数组dp,用于存储最长公共子序列的长度。gridSize 是两个字符串长度中的最大值。填充动态规划表格
遍历两个字符串的每个字符:返回结果
根据dp 表格生成最长公共子序列字符串。假设输入字符串为 "abcde" 和 "ace",最长公共子序列是"ace"`。通过上述算法,我们可以清晰地看到每一步的计算过程,从而理解实现原理。
通过上述方法,我们可以在Objective-C中轻松实现最长公共子序列算法,广泛应用于字符串处理、模式比对等场景。
转载地址:http://seifk.baihongyu.com/