Calcolo delle coordinate di un intersezione tra due segmenti

ZioAntonio1
Salve a tutti i cervelloni matematici....

per esigenze di una programmazione che sto realizzando mi serve
ricavare le coordinate del punto di intersezione tra due segmenti di
cui conosco le coordinate.


Dunque la mia esigenza sarebbe che tramite le coordinate dei 4 punti
riesca a risalire alle coordinate del punto di intersezione senza
scomodare equazioni della retta che sulla carta so ben fare ma non
posso fargliele digerire alla mia programmazione...

mi sapreste aiutare??? Come posso fare???

Grazie in anticipo

Ciao
ZioAntonio

Risposte
freddofede
E' facile, e non dovrebbe servirti neanche l'uso di cicli...

Prendiamo le rette, chiamandole R ed R', nella forma:

$y = mx + q $ (Retta R)
$y' = m'x + q' $ (Retta R')

Sapendo le coordinate di due punti di ciascuna retta, devi innanzitutto ricavarti, ponendoli in opportune variabili, i valori di m e q.
Lavoriamo sulla prima retta: per trovare m e q, chiamando $P_1(x_1, y_1)$ e $P_2(x_2, y_2)$ i due punti per cui passa la retta, e supponendo che tu abbia $x_1, x_2, y_1, y_2$ già memorizzate in variabili, usiamo la formula della retta passante per due punti:

$(y-y_1)/(y_2 - y_1) = (x - x_1)/(x_2 - x_1)$

Da cui si ricava (la formula di sopra l'ho presa da un libro, quelle di sotto le ho ricavate, dovrebbero essere corrette ma ricontrollale per sicurezza):

$m = (y_2-y_1)/(x_2 - x_1)$
$q = (x_2y_1 - x_1y_2)/(x_2 - x_1)$

Analogamente possiamo fare per la seconda retta. Avendo a questo punto ricavato i valori m, m', q, q', e salvati essi in quattro variabili mediante l'assegnamento delle espressioni di sopra, poniamo la condizione:

$mx + q = m'x + q'$

E quindi

$x = (q' - q)/(m - m')$

x è l'ascissa del punto di intersezione, e l'ordinata ce la ricaviamo sostituendo questo valore all'equazione di una delle due rette; non ci dovrebbero essere problemi a fare con qualsiasi linguaggio le operazioni che ti ho detto, tollerando quel minimo di imprecisione dei tipi "float" o "double" se si lavora sulla virgola mobile.

:smt006

ZioAntonio1
Grazie mille...provo a metterlo in pratica e ti faccio sapere!!!


grazie ancora!

Antonio

ZioAntonio1
Rieccomi....


Solo adesso sono riuscito a provare ma purtroppo temo di aver sbagliato qualcosa....
:cry:

Le due rette sono descritte dai seguenti punti:
retta1: point_A al point_d
retta2: point_B al point_e

var m1:Number = Math.floor((point_A.y-point_d.y)/(point_A.x-point_d.x))
var m2:Number = Math.floor((point_B.y-point_e.y)/(point_B.x-point_e.x))
var q1:Number = Math.floor((point_A.x*point_d.y)-(point_d.x*point_A.y)/(point_A.x-point_d.x))
var q2:Number = Math.floor((point_B.x*point_e.y)-(point_e.x*point_B.y)/(point_B.x-point_e.x))
var myX:Number = Math.floor((q2-q1)/(m1-m2))
var myY:Number = Math.floor(m1*myX +q1)

Cosa ho sbagliato??? :(

mircoFN1
Il procedimento di Iore è formalmente corretto ma non è per niente robusto!
La sua applicazione potrebbe dare spiacevoli sorprese, infatti molte variabili intermedie dell'algoritmo potrebbero risultare non definibili, in relazione alla posizione dei 4 pt (o alla scelta degli assi) anche se il problema è ben posto. Per esempio, se due punti sono sulla stessa ascissa, il coefficiente angolare della retta congiungente non è definito (il programma darebbe presumibilemente una divisione per 0).
Io ragionerei così:
1) verificherei l'esistenza della soluzione, ovvero che l'intersezione si possa fare (questo comporta che i quattro punti non siano allineati a due a due)
2) in caso favorevole, scriverei un algoritmo diretto che si ottiene dalla procedura di Iore però sviluppando completamente i calcoli 'a mano' fino al risultato finale (che poi scriverei nel linguaggio scelto)


Caro Antonio, ho l'impressione che se vuoi qualcosa di robusto un po' di algebra te la devi sobbarcare. :wink:

ciao

freddofede
var q1:Number = Math.floor((point_A.x*point_d.y)-(point_d.x*point_A.y)/(point_A.x-point_d.x))
var q2:Number = Math.floor((point_B.x*point_e.y)-(point_e.x*point_B.y)/(point_B.x-point_e.x)) 


Devi racchiudere tra parentesi il numeratore, sennò ne divide solo metà....

Tieni pure conto che almeno non ci siano tutte divisioni esatte, senza resto, la funzione floor può portare una certa perdita di precisione :smt006

P.S.: Che linguaggio stai usando?

ZioAntonio1
Lore hai ragione....rivedendola adesso a mente non fusa ho visto l'errore del numeratore....

Grazie ancora

Uso ActionScript 2 per un progetto fatto in flash.

Ciao

freddofede
"ZioAntonio":
Lore hai ragione....rivedendola adesso a mente non fusa ho visto l'errore del numeratore....

Grazie ancora

Uso ActionScript 2 per un progetto fatto in flash.

Ciao


Segui anche il consiglio di Mirko, e controlla i denominatori con degli if per prevenire divisioni per zero
:smt006

mircoFN1
Se vuoi seguire il mio consiglio.... non mettere IF ai denominatori! Metti gli IF all'inizio per verificare che la coppia di segmenti non sia allineata e poi scrivi l'espressione completa delle coordinate di intersezione senza passaggi intermedi.
Altrimenti devi prevedere una procedura di soluzione quando gli IF non sono rispettati e questo complica non poco l'algoritmo per quei pochi casi patologici.

ciao

ZioAntonio1
Grazie Lore e Grazie Mirko...

superata fase di cottura e rianalizzando il tutto per bene sono giunto a soluzione...

Per la cronaca avevo interpretato male anche funzionalità di Math.Floor che pensavo mi trattasse le virgole mobili...invece mi arrotondava...lascio immaginare il centro dove lo calcolasse!!!!! :D

Fatte le correzioni del caso, ora il centro è perfetto e al deformare la figura si adatta perfettamente il puntatore!

GRAZIE ANCORA...

Alla prossima...domanda!!! :wink:

( devo ancora terminare questo progettino e ho da fare ancora altri calcoli....es. bisettrice)

Ciao
Antonio

freddofede
"mirco59":
Se vuoi seguire il mio consiglio.... non mettere IF ai denominatori! Metti gli IF all'inizio per verificare che la coppia di segmenti non sia allineata e poi scrivi l'espressione completa delle coordinate di intersezione senza passaggi intermedi.
Altrimenti devi prevedere una procedura di soluzione quando gli IF non sono rispettati e questo complica non poco l'algoritmo per quei pochi casi patologici.

ciao


Confermo: così ci guadagni anche in chiarezza.

Rispondi
Per rispondere a questa discussione devi prima effettuare il login.