Java 匹配预定义条件的向量序列中最小索引的搜索算法

Java 匹配预定义条件的向量序列中最小索引的搜索算法,java,algorithm,optimization,search,Java,Algorithm,Optimization,Search,让我们假设我们有固定长度的p序列k。每个序列在0到1.0范围内有两个值。为了简单起见,让我们假设序列只是数组;在实际实现中,它们将被列出 现在,算法需要找到最小的索引,其值表示给定序列中的“主要扰动”。该异常值可以是1.0或超过某个阈值的值(例如0.2)。例如,如果从j-1移动到j时,该值增加超过阈值,那么我们寻求的指数将是j-1 1.0的翻转优先于阈值;例如,如果我们找到一个与阈值匹配的索引,我们仍然应该检查序列是否包含1.0 最后,算法应该生成导致翻转的最小索引。 我已经很快地编写了一些代码

让我们假设我们有固定长度的p序列k。每个序列在01.0范围内有两个值。为了简单起见,让我们假设序列只是数组;在实际实现中,它们将被列出

现在,算法需要找到最小的索引,其值表示给定序列中的“主要扰动”。该异常值可以是1.0或超过某个阈值的值(例如0.2)。例如,如果从j-1移动到j时,该值增加超过阈值,那么我们寻求的指数将是j-1

1.0的翻转优先于阈值;例如,如果我们找到一个与阈值匹配的索引,我们仍然应该检查序列是否包含1.0

最后,算法应该生成导致翻转的最小索引。 我已经很快地编写了一些代码来测试这个概念,并向您展示了我想要的东西。我所寻找的是一个可能更有效的实现,因为这个算法将被广泛执行

List<double[]> nearCaptures = new ArrayList<double[]>();
double threshold = 0.2;
double majorUpset = 1.0;
int[] indexes = new int[nearCaptures.size()];
for (int i = 0; i < nearCaptures.size(); i++) {
    int index = 0;
    double[] tempArray = nearCaptures.get(i);
    Arrays.sort(tempArray);
    int tempIndex = Arrays.binarySearch(tempArray, majorUpset);
    if (tempIndex > 0) {
        for (int j = 1; j < nearCaptures.get(0).length; j++) {
            if (nearCaptures.get(i)[j] == majorUpset) {
                index = j-1;
                break;
            }
        }
    } else {
        for (int j = 1; j < nearCaptures.get(0).length; j++) {
            if (nearCaptures.get(i)[j] >= nearCaptures.get(i)[j-1] + threshold) {
                index = j-1;
                break;
            }
        }
    }
    indexes[i] = index;
}
Arrays.sort(indexes);
System.out.println(indexes[0]);
List nearCaptures=new ArrayList();
双阈值=0.2;
双主加厚=1.0;
int[]index=new int[nearCaptures.size()];
对于(int i=0;i0){
for(int j=1;j=nearCaptures.get(i)[j-1]+阈值){
指数=j-1;
打破
}
}
}
指数[i]=指数;
}
数组。排序(索引);
System.out.println(索引[0]);

提高性能(和正确性)的一些提示:

  • 在查找majorUnder时,执行排序和二进制搜索,结果是O(n log(n))运行时,然后是线性搜索(for循环)。你只需要线性搜索就可以找到是否存在重大问题,以及在哪里存在重大问题

  • 由于
    tempArray
    引用原始数组,因此在对其排序时会弄乱索引。如果需要排序,请对副本进行排序。但是如上所述,您不需要排序

  • 在循环中多次访问值
    nearCaptures.get(i)
    ,最好在
    i
    -循环的开始处将其存储在局部变量中

添加:

您可能希望并行执行搜索,因为一旦在任何数组中找到最小的索引,就可以立即停止搜索

int p = nearCaptures.get(0).length;  // p is the common array length
// search for majorUpset
for(int j = 0; j < p; j++){
  for (double[] arr : nearCaptures) {
    if (arr[j]==majorUpset) return j; // first majorUpset
  }
}
// search for threshold
for(int j = 1; j < p; j++){
  for (double[] arr : nearCaptures) {
    if (arr[j]>arr[j-1]+threshold) return j-1; // first threshold
  }
}
int p=nearCaptures.get(0).length;//p是公共数组长度
//搜索MajorUnder
对于(int j=0;jarr[j-1]+阈值)返回j-1;//第一个阈值
}
}

提高性能(和正确性)的一些提示:

  • 在查找majorUnder时,执行排序和二进制搜索,结果是O(n log(n))运行时,然后是线性搜索(for循环)。你只需要线性搜索就可以找到是否存在重大问题,以及在哪里存在重大问题

  • 由于
    tempArray
    引用原始数组,因此在对其排序时会弄乱索引。如果需要排序,请对副本进行排序。但是如上所述,您不需要排序

  • 在循环中多次访问值
    nearCaptures.get(i)
    ,最好在
    i
    -循环的开始处将其存储在局部变量中

添加:

您可能希望并行执行搜索,因为一旦在任何数组中找到最小的索引,就可以立即停止搜索

int p = nearCaptures.get(0).length;  // p is the common array length
// search for majorUpset
for(int j = 0; j < p; j++){
  for (double[] arr : nearCaptures) {
    if (arr[j]==majorUpset) return j; // first majorUpset
  }
}
// search for threshold
for(int j = 1; j < p; j++){
  for (double[] arr : nearCaptures) {
    if (arr[j]>arr[j-1]+threshold) return j-1; // first threshold
  }
}
int p=nearCaptures.get(0).length;//p是公共数组长度
//搜索MajorUnder
对于(int j=0;jarr[j-1]+阈值)返回j-1;//第一个阈值
}
}

我认为你实际上可能是说,不安是由某个数量级的增加构成的,而不是超过阈值的增加。我不敢改变这个,因为它改变了你写的东西的意义。在这个阈值后面有一个更深的意义,它表达了一个大幅度增加的值,实际上是一个给定染色体的适应值。我不确定这是否是某个数值的大小,但相当恒定,这表明发生了非常不希望发生的事情。我想你实际上可能是说,不安是由某个大小的增加构成的,而不是超过阈值的增加。我不敢改变这个,因为它改变了你写的东西的意义。在这个阈值后面有一个更深的意义,它表达了一个大幅度增加的值,实际上是一个给定染色体的适应值。我不确定这是否是某个值的大小,但相当恒定,表明发生了非常不希望发生的事情。是的,关于查找MajorUnder和分配的要点-谢谢Christian。这只是一个快速的实验代码,看看如何att