2009-09-08 15 views
5

Se espera que esta sea una pregunta matemática muy simple. Si tengo dos series de números, lo que es la manera más simple y más eficiente para comprobar si chocan, por ejemplo:Detectando si dos rangos de números chocan

10-20 and 11-14 // clash as B is contained in A 
11-15 and 20-22 // don't clash 
24-26 and 20-30 // clash as A is contained in B 
15-25 and 20-30 // clash as they overlap at each end 

Actualmente tengo este lío, pero tiene que haber una manera mucho más simple de hacer esta comprobación:

$clash = ($b1 >= $a1 && $b1 <= $a2) 
    || ($b2 >= $a1 && $b2 <= $a2) 
    || ($a1 >= $b1 && $a1 <= $b2) 
    || ($a2 >= $b1 && $a2 <= $b2); 

Respuesta

11

Bueno, primero asegúrese de haber pares bien ordenada (probablemente una buena idea de todos modos, dependiendo de lo que planea hacer con ellos):

if($a1 > $a2) { 
    // swap $a1 and $a2 
    $temp = $a1; 
    $a1 = $a2; 
    $a2 = $temp; 
} 
if($b1 > $b2) { 
    // swap $b1 and $b2 
    $temp = $b1; 
    $b1 = $b2; 
    $b2 = $temp; 
} 

, entonces debería ser capaz de simplificar a:

$clash = ($a2 <= $b1) || ($a1 >= $b2); 

Editar: ¡Vaya, tiene esa prueba al revés! Proveedores:

$clash = !(($a2 <= $b1) || ($a1 >= $b2)); 
+0

Solo iba a publicar eso :-) +1 por ser más rápido. –

+6

o, sin negación: '$ clash = ($ b1 <= $ a2) && ($ a1 <= $ b2)' – sth

+0

Gracias, eso es genial. –

2

Los rangos de no entrar en conflicto si y sólo si $ a2 < = $ b1 o $ a1> = $ b2 (asumiendo que los intervalos se dan como pares ordenados). Ahora niegue la condición.

+1

¿Qué pasa si $ a1> = $ b2? No choca tampoco. –

+0

También asumimos que siempre es el caso que $ a1 <$ a2 y $ b1 <$ b2. –

+0

@Matthew: Derecha @jeffamaphone: Bueno, eso es lo que quiere decir con un "rango", ¿no es así? –

7

creo que debería ser tan simple como esto:

clash = A_LOW <= B_HIGH AND A_HIGH >= B_LOW 
0

Lo que estamos buscando es la intersección de las matrices. http://us3.php.net/array_intersect

Básicamente,

$intersect = array_intersect($arr1, $arr2); 
$clash = (count($intersect) > 0); 

Si los elementos están en tanto arr1 $ y $ arr2, a continuación, se cortan $ mostrará una lista de esos valores. La llamada al conteo() devuelve 1 (o más), por lo que hacer> 0 le da si $ arr1 y $ arr2 tienen elementos similares.

3

ejemplo:
10-20
4 - 11 // esto chocará con arriba
de 1 - 5 // esto chocará con anteriores
40 - 50
almacenar los números en 2 arrays, dicen
x_array = array (10,4,11,40);
y_array = array (20,11,5,50);

asort ($ x_array); // ordenar solo los primeros valores de la matriz x range y mantener el índice
$ max_val = -1;
$ last_index = 0;
foreach ($ x_array como $ each_index => $ each_x) {
    // obtener el valor de Y correspondiente
    $ this_y = $ y_array [$ each_index];
    echo "$ this_y < $ max_val";
    if ($ each_x> $ MAX_VAL & & $ this_y> $ MAX_VAL) {
        $ = $ MAX_VAL this_y;
   }
    else {
        $ = $ last_x x_array [$ LAST_INDEX];
        $ last_y = $ y_array [$ last_index];
        echo "Error: Superposición entre: ($ each_x, $ this_y) y ($ last_x, $ last_y)";
   }
    $ last_index = $ each_index;
}

Cuestiones relacionadas