Java 在二进制搜索失败时查找案例

Java 在二进制搜索失败时查找案例,java,algorithm,Java,Algorithm,我正在尝试解决一个非常有趣的编程挑战,我对代码失败的原因有些不知所措。这是: 编写一个函数,给定一个列表和一个目标和,返回 任意两个不同元素的零基索引,其和等于 目标金额。如果没有此类元素,则函数应 返回null。 例如,findTwoSum(newint[]{1,3,5,7,9},12)应该返回以下任何一个索引元组: 1, 4 (3 + 9 = 12) 2, 3 (5 + 7 = 12) 3, 2 (7 + 5 = 12) 4, 1 (9 + 3 = 12) 应该很简单吧?这是我的函数: p

我正在尝试解决一个非常有趣的编程挑战,我对代码失败的原因有些不知所措。这是:

编写一个函数,给定一个列表和一个目标和,返回 任意两个不同元素的零基索引,其和等于 目标金额。如果没有此类元素,则函数应 返回null。 例如,findTwoSum(newint[]{1,3,5,7,9},12)应该返回以下任何一个索引元组:

1, 4 (3 + 9 = 12)
2, 3 (5 + 7 = 12)
3, 2 (7 + 5 = 12)
4, 1 (9 + 3 = 12)
应该很简单吧?这是我的函数:

public static int[] findTwoSum(int[] list, int sum) {
        int[] indices = null;
        for(int i = 0; i < list.length; i++) {
            int currentNum = list[i];
            int findNum = sum - currentNum;
            int length = list.length;
            int min = i;
            int max = length-1;
                        
            while(max >= min) {
                int guess = (max+min)/2;
                          
                if(list[guess] == findNum) {
                  return new int[] {i,guess};
                } 
                
                if(list[guess] < findNum) {
                    min = guess + 1;
                }
                
                if(list[guess] > findNum) {
                    max = guess - 1;
                }
            }
            
        }
       
        
        return indices;
    }
公共静态int[]findTwoSum(int[]list,int-sum){
int[]索引=null;
for(int i=0;i=最小值){
int guess=(最大+最小)/2;
如果(列表[猜测]==findNum){
返回新的int[]{i,guess};
} 
如果(列出[猜测]findNum){
max=guess-1;
}
}
}
回报指数;
}

代码非常简单,对于数组中的每个元素,它都会尝试使用二进制搜索查找另一个元素,以便它们的和等于提供的。我已经测试了这段代码,但我找不到它失败的场景,假设提供的数组已排序。然而,当我在上运行这段代码时,最后一个案例失败了,这是一个错误的解决方案。有人能指出这种方法的错误吗?

代码假定列表已排序。问题语句没有说明元素的顺序,因此您需要自己对数组进行排序。因为需要索引,所以需要对值和索引对进行排序


一种更快的方法是将数据放入带有计数和原始索引的哈希映射中,并检查列表中每个
n
是否存在
Target-n
。当
Target
等于
2*n

时,需要对特殊情况进行计数。根据作者关于初始列表排序顺序的问题和说明,初始列表似乎未排序。因此,需要对列表进行排序,并且原始索引需要单独存储在另一个列表中

在对数组进行排序并记录原始索引之后,让我们假设
arr[]
包含排序列表,
index[]
包含
arr[]
中相应元素的原始索引。简单地说,
index[i]
给出元素
arr[i]
的原始索引

现在,您可以按照2和算法查找配对:

  • 初始化两个索引变量以查找候选变量 排序数组中的元素

    • 首先初始化到最左边的索引:l=0
    • 初始化第二个最右边的索引:r=ar_size-1
  • 当l
    • 如果(arr[l]+arr[r]==sum),则返回对(索引[l],索引[r])
    • 否则如果(arr[l]+arr[r]
    • 否则r--
  • 整个数组中没有候选项-返回
    NULL
您还可以使用二进制搜索技术代替2和过程


希望能有帮助

试试这个解决方案。它对数组进行排序,并使用二进制搜索来定位第二个元素,该元素必须是sum-n

如果找到匹配对,则在原始数组中查找该对以确定原始索引:

public static int[] findTwoSum(int[] list, int sum) {
    int len = list.length;
    int[] sortedList= Arrays.copyOf(list, len);
    Arrays.sort(sortedList);
    for (int i = 0; i < len; i++) {
        int m = list[i];
        int j = Arrays.binarySearch(sortedList, sum - m);
        if (j >= 0 && i != j)
            return new int[] { i, findIndex(list, sortedList[j]) };
    }
    return null;
}

public static int findIndex(int[] list, int m) {
    int len = list.length;
    for (int i = 0; i < len; i++) {
        if (list[i] == m)
            return i;
    }
    return -1;
}
公共静态int[]findTwoSum(int[]list,int-sum){
int len=list.length;
int[]sortedList=Arrays.copyOf(列表,len);
数组。排序(sortedList);
对于(int i=0;i=0&&i!=j)
返回新的int[]{i,findIndex(list,sortedList[j]);
}
返回null;
}
公共静态int findIndex(int[]列表,int m){
int len=list.length;
对于(int i=0;i
该问题要求列表中有两个不同的元素,您的代码似乎无法正确处理这些元素。@Gassa是的,我也对此进行了检查,但实际上没有帮助。我现在想的是,可能是数组在最后一种情况下没有排序。给定的列表是否已经以排序形式存在?@User\u Targaryen我希望是这样,但我可能错了。所以我想我需要先对它进行排序并跟踪原始索引。@Zed:那肯定是问题所在。…(
一种比搜索所选数字和目标和之间的差更快的方法)一种更简单的方法(二进制)只搜索与第一个数字的差异,并从第一个开始向下移动两个索引,直到它们相遇(唯一对)或到达另一个开始(问题如前所述/本部分所述)。