二进制搜索,数组索引越界Java
首先,我想说的是,我不是在寻求答案,而是更多的建议,以便我能从这个问题中学习。每次运行代码时,我都会在ArrayOperations java文件的第254行上得到超出范围的数组索引二进制搜索,数组索引越界Java,java,arrays,binary-search,Java,Arrays,Binary Search,首先,我想说的是,我不是在寻求答案,而是更多的建议,以便我能从这个问题中学习。每次运行代码时,我都会在ArrayOperations java文件的第254行上得到超出范围的数组索引 if (SearchKey == tempArray[middle]) 我已经在代码中添加了尽可能多的检查,并尽可能多地对其进行了注释,以方便您使用。我再一次在寻找关于这方面的建议,如果可能的话,不仅仅是一个直接的答案。这个错误似乎总是给了我1/2数据项的负面版本 例如:100000个数据项,数组索引超出范围:-
if (SearchKey == tempArray[middle])
我已经在代码中添加了尽可能多的检查,并尽可能多地对其进行了注释,以方便您使用。我再一次在寻找关于这方面的建议,如果可能的话,不仅仅是一个直接的答案。这个错误似乎总是给了我1/2数据项的负面版本
例如:100000个数据项,数组索引超出范围:-49999
import javax.swing.*;
// File-related imports
import java.io.IOException;
import java.util.Scanner;
import java.io.File;
public class ArrayOperations
{
// File Parameters
String DataFilePath;
String DataFileName;
String KeysFilePath;
String KeysFileName;
int NumberOfDataItems;
int NumberOfKeys;
int N;
int BucketHashArraySize;
int NoBuckets;
//Array
int[] OriginalArray = new int[1000000];
int[] SortedArray = new int[1000000];
int[] HashedArray = new int[2000000];
int[] BucketHashedArray = new int[2000000];
int[] KeysArray = new int[1000000];
long SSAverageAccessTime;
long SSAverageCompSuc;
long SSAverageCompFailed;
long SSNumberKeysSuc;
long SSNumberKeysFailed ;
long BSAverageAccessTime;
long BSAverageCompSuc ;
long BSAverageCompFailed;
long BSNumberKeysSuc ;
long BSNumberKeysFailed ;
long HSAverageAccessTime;
long HSAverageCompSuc ;
long HSAverageCompFailed;
long HSNumberKeysSuc ;
long HSNumberKeysFailed ;
public ArrayOperations()
{
// File Parameters
DataFilePath = null;
DataFileName = null;
KeysFilePath = null;
KeysFileName = null;
NumberOfDataItems=0;
NumberOfKeys =0;
N =0;
BucketHashArraySize = 0;
NoBuckets =0;
// Statistics
SSAverageAccessTime = 0;
SSAverageCompSuc = 0;
SSAverageCompFailed = 0;
SSNumberKeysSuc = 0;
SSNumberKeysFailed = 0;
}
public void ReadDataFile() throws IOException
{
JFileChooser chooser = new JFileChooser();
chooser.setDialogType(JFileChooser.OPEN_DIALOG );
chooser.setDialogTitle("Open Data File");
int returnVal = chooser.showOpenDialog(null);
if( returnVal == JFileChooser.APPROVE_OPTION)
{
DataFilePath = chooser.getSelectedFile().getPath();
DataFileName = chooser.getSelectedFile().getName();
}
// read data file and copy it to original array
if (DataFilePath != null)
{
try
{
int index = 0;
Scanner integerTextFile = new Scanner(new File(DataFilePath));
while (integerTextFile.hasNext())
{
// read the next integer
OriginalArray[index] = integerTextFile.nextInt();
index++;
}
// end of file detected
integerTextFile.close();
NumberOfDataItems = index;
}
catch (IOException ioe)
{
System.exit(0);
}
}
else
NumberOfDataItems = 0;
}
public void ReadKeysFile() throws IOException
{
JFileChooser chooser = new JFileChooser();
chooser.setDialogType(JFileChooser.OPEN_DIALOG );
chooser.setDialogTitle("Open Keys File");
int returnVal = chooser.showOpenDialog(null);
if( returnVal == JFileChooser.APPROVE_OPTION)
{
KeysFilePath = chooser.getSelectedFile().getPath();
KeysFileName = chooser.getSelectedFile().getName();
}
// read data file and copy it to original array
if (KeysFilePath != null)
{
try
{
int index = 0;
Scanner integerTextFile = new Scanner(new File(KeysFilePath));
while (integerTextFile.hasNext())
{
// read the next integer
KeysArray[index]= integerTextFile.nextInt();
index++;
}
// end of file detected
integerTextFile.close();
NumberOfKeys = index;
}
catch (IOException ioe)
{
System.exit(0);
}
}
else
NumberOfKeys = 0;
}
public void SequentialSearch()
{
SSAverageAccessTime = 0;
SSAverageCompSuc = 0;
SSAverageCompFailed = 0;
SSNumberKeysSuc = 0;
SSNumberKeysFailed = 0;
int SearchKey;
int TotalNumberOfComparisons;
long startTime = System.nanoTime();
boolean found = false;
for (int k=0; k<NumberOfKeys; k++)
{
found = false;
SearchKey = KeysArray[k];
TotalNumberOfComparisons = 0;
for (int d=0; d<NumberOfDataItems; d++)
{
TotalNumberOfComparisons++;
if (SearchKey == OriginalArray[d])
{
found = true;
}
if (found)break;
}
if(found)
{
SSAverageCompSuc = SSAverageCompSuc + TotalNumberOfComparisons;
SSNumberKeysSuc ++;
}
else
{
SSAverageCompFailed = SSAverageCompFailed + TotalNumberOfComparisons;
SSNumberKeysFailed ++;
}
}
long estimatedTime = System.nanoTime() - startTime;
if (NumberOfKeys != 0)
SSAverageAccessTime = Math.round((estimatedTime/NumberOfKeys));
else
SSAverageAccessTime = 0;
if(SSNumberKeysSuc != 0)
SSAverageCompSuc = Math.round (SSAverageCompSuc / SSNumberKeysSuc) ;
else
SSAverageCompSuc = 0;
if (SSNumberKeysFailed != 0)
SSAverageCompFailed = Math.round (SSAverageCompFailed / SSNumberKeysFailed) ;
else
SSNumberKeysFailed = 0;
return;
}
public void BinarySearch()
{
// makes a temporary array the length of the number of data items we gave it int[] tempArray = new int[NumberOfDataItems];
// copies a portion of the original array (origionalArray = new int[1000000] above) that has the data inputs
// we are copying only the portion of the original array the was given the data inputs when we opened the data item .txt
for (int i = 0; i < NumberOfDataItems; i ++)
{
tempArray[i]=OriginalArray[i];
}
// takes the temporary array and sorts it
java.util.Arrays.sort(tempArray);
BSAverageAccessTime = 0;
BSAverageCompSuc = 0;
BSAverageCompFailed = 0;
BSNumberKeysSuc = 0;
BSNumberKeysFailed = 0;
int SearchKey;
int TotalNumberOfComparisons;
long startTime = System.nanoTime();
boolean found = false;
int low = 0;
int high = tempArray.length-1;
// sets the midpoint
int middle = (low-high)/2;
for(int k = 0; k<NumberOfKeys; k++)
{
SearchKey = KeysArray[k];
TotalNumberOfComparisons = 0;
for (int d=0; d< Math.log(tempArray.length -1); d++)
{
TotalNumberOfComparisons++;
// makes sure low doesn't go out of bounds
if (low < 0)
{
low = 0;
}
// make sure high doesn't go out of bounds
if(high >= tempArray.length)
{
high = tempArray.length-1;
}
// checks the midpoint against the key we are using
if (SearchKey == tempArray[middle])
{
found = true;
}
// makes sure that if the midpoint doesn't equal the key we get false
else
if (low == high && SearchKey != tempArray[middle])
{
found = false;
}
// if the key is greater than the middle we check the upper portion
else
if (SearchKey > tempArray[middle])
{
low = (middle +1);
}
// if the key is less than the middle we check the lower portion
else
if (SearchKey < tempArray[middle])
high = (middle -1);
if (found)break;
}
if(found)
{
BSAverageCompSuc = BSAverageCompSuc + TotalNumberOfComparisons;
BSNumberKeysSuc ++;
}
else
{
BSAverageCompFailed = BSAverageCompFailed + TotalNumberOfComparisons;
BSNumberKeysFailed ++;
}
}
long estimatedTime = System.nanoTime() - startTime;
if (NumberOfKeys != 0)
BSAverageAccessTime = Math.round((estimatedTime/NumberOfKeys));
else
BSAverageAccessTime = 0;
if(BSNumberKeysSuc != 0)
BSAverageCompSuc = Math.round (BSAverageCompSuc / BSNumberKeysSuc) ;
else
BSAverageCompSuc = 0;
if (BSNumberKeysFailed != 0)
BSAverageCompFailed = Math.round (BSAverageCompFailed / BSNumberKeysFailed) ;
else
BSNumberKeysFailed = 0;
return;
}
public void HashedSearch()
{
HSAverageAccessTime = 0;
HSAverageCompSuc = 0;
HSAverageCompFailed = 0;
HSNumberKeysSuc = 0;
HSNumberKeysFailed = 0;
int SearchKey;
int TotalNumberOfComparisons;
long startTime = System.nanoTime();
boolean found = false;
}
public int FindPrime()
{
return 0;
}
public void Initialize()
{
}
public void BHSearch()
{
}
}
你计算错了 更改如下:
int middle = (low-high)/2;
致:
low总是小于high,所以您得到的是一个负数,并且该负数索引将不存在于您的数组中
虽然我没有检查任何其他可能的问题或算法的有效性,如果有人能告诉我二进制搜索函数有什么问题,或者我将原始数组的一部分复制到TempArray的方式有什么问题,或者如果我遗漏了一些愚蠢的东西,我将不胜感激,那么以上就是您遇到的问题的解决方案。就像我说的,我更喜欢建议而不是直接的答案,所以我可以从中学习,当你在做tempArray[middle]middle is-1时,因为你在做:int high=tempArray.length-1。所以,当tempArray为0时,得到-1。您可以这样做:int high=tempArray.length>0?tempArray.length-1:0;TL;DR请使用Java命名约定-变量为camelCase。请使用调试器隔离问题。请格式化你的代码。@Fede我刚刚试过,谢谢你的建议,但没有得到基本上-NumberOfDataInputs*.5,而是用一个额外的-1@BoristheSpider哇,嗯,不知什么原因,我以前没被教过如何使用调试器?但现在,我在对eclipse进行了简短的搜索之后找到了它,我不得不说非常感谢
int middle = (low-high)/2;
int middle = (high-low)/2;