Java 在另一个字符串中搜索字符串数组的最有效方法

Java 在另一个字符串中搜索字符串数组的最有效方法,java,arrays,performance,algorithm,Java,Arrays,Performance,Algorithm,我有一大串字符串,看起来像这样: 字符串温度[]=新字符串[200000] 我还有一个字符串,我们称之为bigtext。我需要做的是遍历temp的每个条目,检查该条目是否在bigtext中找到,然后根据它做一些工作。因此,骨架代码如下所示: for (int x = 0; x < temp.length; x++) { if (bigtext.indexOf(temp[x]) > -1 { //do some stuff } else continue; } for(

我有一大串字符串,看起来像这样: 字符串温度[]=新字符串[200000]

我还有一个字符串,我们称之为bigtext。我需要做的是遍历temp的每个条目,检查该条目是否在bigtext中找到,然后根据它做一些工作。因此,骨架代码如下所示:

for (int x = 0; x < temp.length; x++) {
  if (bigtext.indexOf(temp[x]) > -1 {

  //do some stuff
  } else continue;
}
for(int x=0;x-1{
//做点什么
}否则继续;
}
因为temp中有很多条目,也有很多bigtext的实例,所以我想以最有效的方式来做这件事。我想知道我所概述的是不是迭代搜索的最有效方式,是否有更好的方法来做这件事

谢谢

Elliott

这是一种非常有效的方法。只需对
temp.length
进行一次评估,您就可以稍微改进它

for(int x = 0, len = temp.length; x < len; x++)
for(int x=0,len=temp.length;x

尽管您没有提供足够的程序细节,但很有可能通过重新设计程序找到更有效的方法。

如果您有关于
temp
的其他信息,您可以改进迭代


如果并行化迭代,还可以减少所花费的时间。

另一种方法是对文本进行标记化,比如说用常用标点符号分割。然后将这些标记放入
集合中,然后找到与主容器相交的部分

不要用数组,也要把单词放在
集合中

bidTextSet.retainAll(mainWordsSet);

剩下的将是出现在你“字典”中的
bigText
中的单词。

效率在很大程度上取决于对你有价值的东西

您是否愿意增加内存以缩短时间?您是否愿意增加时间以高效处理大型数据集?您是否愿意增加CPU核心的争用?您是否愿意进行预处理(可能是一种或多种形式的索引)以缩短关键部分的查找时间


在你的报价中,你指出了你想要提高效率的全部部分,但这意味着你已经排除了代码或系统中可以进行权衡的任何部分。这迫使人们想象你关心什么和你不关心什么。很有可能所有贴出的答案都是正确的和不正确的从一个人的角度来看。

使用像Boyer Moore这样的搜索算法。Google Boyer Moore,它有很多链接来解释它是如何工作的。例如,有。

我想你正在寻找一种像or这样的算法,它被设计成在文本中并行搜索大量子字符串。

请注意,你当前的completexity是
O(| S1 |*n)
,其中
|S1 |
bigtext
的长度,
n
是数组中的元素数,因为每次搜索实际上都是
O(| S1 |)


通过
bigtext
构建一个数组,并迭代数组中的元素,您可以将这种复杂性降低到
O(|S1 |+| S2 |*n)
,其中
| S2 |
是数组中最长字符串的长度。假设
| S2 |,恐怕无论如何它都没有效率

要选择正确的算法,您需要提供一些答案:

  • 什么是离线计算的?也就是说,
    bigText
    事先就知道了吗?从它的名字来看,我想
    temp
    不是
  • 你真的在找单词吗?如果是的话,。也能帮上忙
  • 如果你需要一点模糊性,可以使用stem或soundex吗

  • 坚持严格的包含测试,您可能会从
    temp
    数组中构建一个。这将阻止多次搜索同一子字符串。

    这是20万个字符串!搜索引擎,反向索引…不确定我是否有意义(:嗯,如果是字符串比较,你可以先检查两个字符串的长度,如果相等,然后比较从最后一个字符开始的字符串,如果你的字符串可能非常相似,但在最后几个字符中有所不同。你在寻找算法吗?你将使用什么效率度量?你确定这是一种改进吗java中的ement?我不知道数组的情况,但java在ArrayList上的迭代速度更快,例如,如果条件是xList
    对象是不同的,有
    size()
    在恒定时间
    O(1)
    中运行,而
    array.length
    O(n)
    中运行。那么一个聪明的编译器可能会执行一些优化。似乎之前已经讨论过了:@Johan为什么要
    array.length
    在O(n)中运行?它是最后一个整数属性,就像
    list.size()一样
    是一个普通整数属性的获取者,当然
    做一些事情
    依赖于以前的迭代。如果不是,并行化绝对是一个好主意。并行化可能是一个好处,但我们真的不知道他们是否有额外的内核来利用它。协调thre是有成本的如果只有一个有效的内核可用,那么并行化可能会带来昂贵的开销。即使在单内核环境中,对200000个元素进行并行化也可以提高速度;无论如何,值得一试同意@Hachi,即使只有一个内核,运行多个线程——每次都有pagefault和PageNeeds将从磁盘重新加载到内存-使用多线程系统-其他线程在等待磁盘时继续工作,而使用单线程时,程序只是挂起