我有一个直接缓冲区,里面有已经排序的整数(即1,1,3,3,3,7,7,…)。大多数值都会出现多次。我想找到我搜索的值的第一个位置。
- 是否有直接作用于缓冲区的搜索功能内置于Java中?(找不到任何东西)
- 如果没有,有没有像样的库提供这样的功能
-
如果没有,建议使用什么搜索算法来实现,假设:
- 我的缓冲区中通常会有数百万个条目
- 速度非常重要
- 它必须返回搜索到的数字的第一次出现
- 我宁愿不让它修改数据,因为之后我需要原始数据
编辑:感谢所有建议Arrays.binarySearch()
的海报,但据我所知,直接缓冲区通常没有后备阵列。这就是为什么我在寻找一个直接在缓冲区上工作的实现。
此外,每个值最多可能出现一千次,因此在找到着陆点后进行线性搜索可能不是很有效。不过,dasblinkenlight的比较建议可能会奏效。
最好的方法是为缓冲区编写自己的二进制搜索实现。这种方法小心地避免了与创建视图、复制大型阵列等相关的潜在性能损失,同时保持紧凑。
链接处的代码示例返回最右边的点;需要将nums[guess] > check
线上的>
替换为>=
才能得到最左边的点。这可以节省潜在的向后线性搜索成本,或者使用"向后"Comparator
,这需要将int
封装到Integer
对象中。
使用二进制搜索算法
ByteBuffer buffer = createByteBuffer();
IntBuffer intBuffer = buffer.asIntBuffer();
如果字节数组可以转换为int数组,请使用:
int [] array = intBuffer.array();
int index = java.util.Arrays.binarySearch(array,7);
我不知道缓冲区的内置功能(Arrays.binarySearch(...)
需要将缓冲区转换为数组),但对于3.:由于缓冲区已经排序,二进制搜索可能很有用。如果你找到了这个值,你可以检查之前的值,以获得该序列的开始。
您可能需要编写自己的二进制搜索:如果检查的值与搜索的值相等,则该搜索总是向左移动。
因此,实际上,您要搜索的不是x
,而是x-ε
。你的算法总是需要logn(或logn+1)步,因为它总是"失败",但它会给你第一个大于x-ε
的元素的索引。您所需要做的就是检查该元素是否为x
,如果是,则表示您找到了匹配项,如果不是,则表示缓冲区中没有x
。