Java中实现KMP字符串匹配算法详解

版权申诉
0 下载量 39 浏览量 更新于2024-11-09 收藏 628B RAR 举报
资源摘要信息:"KMP算法(Knuth-Morris-Pratt)是一种高效的字符串匹配算法,它可以在O(n+m)的时间复杂度内完成对目标字符串S(长度为n)和模式字符串P(长度为m)的匹配过程。该算法由Donald Knuth、Vaughan Pratt和James H. Morris共同发明,主要用于解决字符串搜索问题。在Java编程中实现KMP算法,可以有效地提高字符串匹配的效率,尤其适用于文本编辑器、数据库、搜索引擎等需要进行大量字符串匹配的场合。 KMP算法的核心在于一个前缀函数(也称部分匹配表或失败函数),该函数用于在模式字符串内部进行部分匹配。具体来说,前缀函数会计算出模式字符串P中每个位置之前字符串的最长相等前后缀的长度,这个信息被用来在不匹配的情况下移动模式字符串,而不是像朴素的字符串匹配算法那样逐个字符地移动模式字符串。 前缀函数的设计关键在于当模式字符串P与目标字符串S在某个位置i不匹配时,由于前缀函数已经包含了P中所有可能的重复信息,我们可以直接利用这些信息来将模式字符串P向右移动至合适的位置,从而保证在S中继续搜索时不会遗漏任何一个可能的匹配起始位置。 下面是Java实现KMP算法的核心代码,将展现如何构建前缀函数以及如何使用它来高效匹配字符串: ```java public class KMP { public int[] computePrefixFunction(String pattern) { int m = pattern.length(); int[] prefix = new int[m]; prefix[0] = 0; int k = 0; for (int i = 1; i < m; i++) { while (k > 0 && pattern.charAt(k) != pattern.charAt(i)) { k = prefix[k - 1]; } if (pattern.charAt(k) == pattern.charAt(i)) { k++; } prefix[i] = k; } return prefix; } public int KMPSearch(String text, String pattern) { int n = text.length(); int m = pattern.length(); int[] prefix = computePrefixFunction(pattern); int q = 0; // 数量,即模式字符串匹配到的位置 for (int i = 0; i < n; i++) { while (q > 0 && pattern.charAt(q) != text.charAt(i)) { q = prefix[q - 1]; } if (pattern.charAt(q) == text.charAt(i)) { q++; } if (q == m) { return i - m + 1; // 找到匹配,返回模式字符串开始的位置 } } return -1; // 未找到匹配 } public static void main(String[] args) { KMP kmp = new KMP(); String text = "ABC ABCDAB ABCDABCDABDE"; String pattern = "ABCDABD"; int result = kmp.KMPSearch(text, pattern); if (result != -1) { System.out.println("模式字符串在文本中的位置起始于: " + result); } else { System.out.println("未找到匹配的模式字符串"); } } } ``` 在上述代码中,首先通过`computePrefixFunction`方法计算模式字符串P的前缀函数。然后在`KMPSearch`方法中使用这个前缀函数来进行高效的模式匹配。通过模拟在文本字符串S中逐个字符比较,并利用前缀函数避免重复比较已知的字符,从而实现快速匹配。在`main`方法中,我们通过一个具体的示例演示了如何使用KMP算法进行字符串匹配。 在Eclipse或其他Java开发环境中,用户可以创建一个新的Java项目,将上述代码保存为KMP.java文件,并通过构建和运行该文件来测试KMP算法的执行效率和正确性。"

import numpy import numpy as np import matplotlib.pyplot as plt import math import torch from torch import nn from torch.utils.data import DataLoader, Dataset import os os.environ['KMP_DUPLICATE_LIB_OK']='True' dataset = [] for data in np.arange(0, 3, .01): data = math.sin(data * math.pi) dataset.append(data) dataset = np.array(dataset) dataset = dataset.astype('float32') max_value = np.max(dataset) min_value = np.min(dataset) scalar = max_value - min_value print(scalar) dataset = list(map(lambda x: x / scalar, dataset)) def create_dataset(dataset, look_back=3): dataX, dataY = [], [] for i in range(len(dataset) - look_back): a = dataset[i:(i + look_back)] dataX.append(a) dataY.append(dataset[i + look_back]) return np.array(dataX), np.array(dataY) data_X, data_Y = create_dataset(dataset) train_X, train_Y = data_X[:int(0.8 * len(data_X))], data_Y[:int(0.8 * len(data_Y))] test_X, test_Y = data_Y[int(0.8 * len(data_X)):], data_Y[int(0.8 * len(data_Y)):] train_X = train_X.reshape(-1, 1, 3).astype('float32') train_Y = train_Y.reshape(-1, 1, 3).astype('float32') test_X = test_X.reshape(-1, 1, 3).astype('float32') train_X = torch.from_numpy(train_X) train_Y = torch.from_numpy(train_Y) test_X = torch.from_numpy(test_X) class RNN(nn.Module): def __init__(self, input_size, hidden_size, output_size=1, num_layer=2): super(RNN, self).__init__() self.input_size = input_size self.hidden_size = hidden_size self.output_size = output_size self.num_layer = num_layer self.rnn = nn.RNN(input_size, hidden_size, batch_first=True) self.linear = nn.Linear(hidden_size, output_size) def forward(self, x): out, h = self.rnn(x) out = self.linear(out[0]) return out net = RNN(3, 20) criterion = nn.MSELoss(reduction='mean') optimizer = torch.optim.Adam(net.parameters(), lr=1e-2) train_loss = [] test_loss = [] for e in range(1000): pred = net(train_X) loss = criterion(pred, train_Y) optimizer.zero_grad() # 反向传播 loss.backward() optimizer.step() if (e + 1) % 100 == 0: print('Epoch:{},loss:{:.10f}'.format(e + 1, loss.data.item())) train_loss.append(loss.item()) plt.plot(train_loss, label='train_loss') plt.legend() plt.show()请适当修改代码,并写出预测值和真实值的代码

2023-06-09 上传