Introducción
La dicotomía es uno de los algoritmos de divide y vencerás entre los cinco algoritmos básicos. De acuerdo con la idea de divide y vencerás de los algoritmos de divide y vencerás, la idea de dicotomía es muy simple, a saber:
- Divida el intervalo en dos partes y determine a qué parte pertenece el elemento de búsqueda.
- Actualice el intervalo y repita el primer paso. Hasta que el intervalo se reduzca a un solo elemento.
El método de búsqueda binaria tiene limitaciones relativamente grandes en el uso real. El método de búsqueda binaria debe cumplir con los siguientes requisitos:
- Debe utilizar una estructura de almacenamiento secuencial , como una matriz o una lista vinculada. La recolección no es aceptable.
- Deben disponerse en orden, es decir, están ordenados cuando se almacenan.
Por ejemplo
Por ejemplo: una matriz de 10 dígitos, almacene 10 letras de la a a la z en orden, que contiene la letra x. Calcula la letra x según la dicotomía.
una | C | re | F | j | l | norte | q | X | con |
Primero encuentre el elemento j en el medio de la matriz (j o l está bien, tome j como ejemplo), j es menor que x, y los elementos se almacenan en la matriz en orden, luego x debe estar entre j y z.
- Tome el elemento n entre j y z, y n sigue siendo menor que x.
- Tome el elemento q entre n y z, y q es menor que x.
- Tome el elemento en el medio de q ~ z y encuentre x.
Lo anterior es un ejemplo simple de búsqueda binaria. Si usa la implementación de código, debe usar la recursividad. La dificultad radica en:
- Cómo determinar las condiciones de terminación;
- Cuando haya dos medianas, cuál se tomará;
- Cómo obtener el valor correcto cuando solo hay dos elementos en el último intervalo;
solicitud
Aquí hay un ejemplo:
Encuentra el número de duplicados:
Dada una matriz de números que contiene n + 1 enteros, cuyos números están todos entre 1 y n (incluidos 1 y n), sabemos que hay al menos un entero repetido. Suponiendo que solo hay un entero repetido, calcule el número repetido.
Ejemplo 1:
输入: [1,3,4,2,2]
输出: 2
Fuente: LeetCode
Enlace: Enlace del título original
Ideas:
Las siguientes condiciones se pueden extraer del título:
- Solo hay un número repetido;
- Todos los números están en el rango de n;
- Hay un total de n + 1 elementos;
La pregunta solo requiere encontrar el valor del elemento repetido y no se preocupa por la posición del elemento, por lo que puede usar la dicotomía para encontrarlo.
Debido a que todos los elementos están entre 1 y n, y solo se repite un elemento, asumiendo que no hay tal número repetido, entonces el número de elementos menores que n / 2 en esta matriz debe ser el mismo que el número de elementos mayores que n / 2 . Si agrega este número, el equilibrio se rompe y puede juzgar si el número pertenece a un intervalo mayor que n / 2 o un intervalo menor que n / 2.
Itere con esto como clave y finalmente obtenga el valor de este elemento repetido.
Código:
package leetcode;
public class FindDuplicate {
int num = 0;
public int findDuplicate(int[] nums) {
int minLine = 1;
int maxLine = nums.length-1;
dichotomySearch(minLine,maxLine,nums);
return num;
}
public void dichotomySearch(int minLine,int maxLine,int[] nums) {
int flag = 0;
int median = (minLine + maxLine)/2;
//only two number
if(minLine==maxLine-1||minLine==maxLine){
for (int i = 0; i < nums.length; i++) {
if (nums[i]==minLine){
flag++;
}
}
if (flag>1){
num = minLine;
}else {
num = maxLine;
}
return;
}
for (int i = 0; i < nums.length; i++) {
if (nums[i] < median && nums[i]>=minLine){
flag--;
}
if (nums[i] > median && nums[i]<=maxLine){
flag++;
}
}
if (flag<=0){
maxLine = median;
dichotomySearch(minLine,maxLine,nums);
}else {
minLine = median;
dichotomySearch(minLine,maxLine,nums);
}
}
public static void main(String[] args) {
int[] nums = {1,1};
FindDuplicate findDuplicate = new FindDuplicate();
System.out.println(findDuplicate.findDuplicate(nums));
}
}