Пересечение отрезков на плоскости - Free Pascal

Узнай цену своей работы

Формулировка задачи:

Подскажите, пожалуйста, нужно определить пересекаются ли отрезки, если да, то не наложены ли они друг на друга (хотя бы частично). В моем коде не предусмотрено только наложение, ибо не знаю как его сделать
var
  k1,k2: real;
  x1,y1,x2,y2,x3,y3,x4,y4: real;
  x,y: real;
 
  function per(): boolean;
  var
    k1, k2, k3, k4: real;
  begin
    k1 := (x4 - x3) * (y1 - y3) - (y4 - y3) * (x1 - x3);
    k2 := (x4 - x3) * (y2 - y3) - (y4 - y3) * (x2 - x3);
    k3 := (x2 - x1) * (y1 - y1) - (y2 - y1) * (x3 - x1);
    k4 := (x2 - x1) * (y2 - y1) - (y2 - y1) * (x4 - x1);
    per := (k1 * k2 <= 0) and (k3 * k4 <= 0);
  end;
 
begin
  readln(x1,y1,x2,y2);
  readln(x3,y3,x4,y4);
 
  if(per)then
    writeln(2)
  else if (((x1<=x)and(x2>=x)and(x3<=x)and(x4>=x))or((y1<=y)and(y2>=y)and(y3<=y)and(y4>=y))) then
    writeln(1)
  else
    writeln(0);
  readln;
end.

Решение задачи: «Пересечение отрезков на плоскости»

textual
Листинг программы
type
  point = record
    x, y: integer;
  end;
  otr = record
    x, y: point;
  end;
 
var
  a,b,c,d: point;
 
function bts(a,b,c: point): boolean;
var
  x1, x2,x3,y1,y2,y3: integer;
  a1, b1: real;
begin
  x1 := a.x;
  y1 := a.y;
  x2 := b.x;
  y2 := b.y;
  x3 := c.x;
  y3 := c.y;
  if(x1=x2)then begin
    writeln(x1, x2);
    if((y3>=y1)and(y3<=y2)) or((y3<=y1)and(y3>=y2)) then bts := true
      else bts := false
  end
    else begin
      a1:=(y1-y2)/(x1-x2);
      b1:=((y1+y2)-a1*(x1+x2))/2;
      if (y3 = a1*x3+b1) and (x3 > x1) and (x3 < x2) or (y3 = a1*x3+b1) and (x2 > x1) and (x3 < x1)then bts := true
        else bts := false;
    end;
  end;
 
function sign(n: real): integer;
begin
  if(n > 0) then sign := 1
    else if(n < 0) then sign := -1
      else sign := 0;
end;
 
function cp(a, b, c, d: point): integer;
 
  var
    vec1, vec2: point;
  begin
    vec1.x := (b.x -a.x);
    vec1.y := (b.y -a.y);
    vec2.x := (d.x -c.x);
    vec2.y := (d.y -c.y);
    cp := vec1.x * vec2.y - vec1.y * vec2.x;
  end;
 
begin
  read(a.x, a.y, b.x, b.y);
  read(c.x, c.y, d.x, d.y);
  if (cp(a, b, c, d) <> 0) and (sign(cp(a, b, a, c)) <> sign(cp(a, b, a, d))) and (sign(cp(c, d, c, a)) <> sign(cp(c, d, c, b))) then
    writeln(1)
  else if   (bts(a, c, d)) or (bts(b, c, d)) or (bts(c, a, b)) or (bts(d, a, b))   then
    writeln(2)
  else
    writeln(0);
  readln;
  readln;
end.

Объяснение кода листинга программы

  1. Переменные типа point используются для представления точек на плоскости и содержат значения координат x и y.
  2. Переменные типа otr используются для представления отрезков на плоскости и содержат значения координат точек начала и конца отрезка.
  3. В функции bts(a,b,c: point): boolean; происходит проверка, пересекаются ли отрезки a-b и b-c. Если пересекаются, то функция возвращает true, иначе - false.
  4. В функции sign(n: real): integer; определяется знак числа n.
  5. В функции cp(a, b, c, d: point): integer; вычисляется скалярное произведение векторов ab и cd, которое используется для определения, являются ли отрезки a-b и c-d параллельными или пересекающимися.
  6. В основной части программы считываются координаты точек a, b, c и d, затем вызывается функция cp(a, b, c, d) для вычисления скалярного произведения векторов ab и cd.
  7. Если скалярное произведение не равно нулю и знаки скалярных произведений векторов ab и cd с векторами ca и cb соответственно различны, то это означает, что отрезки a-b и c-d пересекаются.
  8. Если условие из пункта 7 выполняется, то выводится сообщение 1, иначе проверяется, пересекаются ли отрезки a-b и c-d с помощью функции bts(a, c, d) или bts(b, c, d).
  9. Если условие из пункта 8 выполняется, то выводится сообщение 2, иначе выводится сообщение 0, что означает, что отрезки не пересекаются.

ИИ поможет Вам:


  • решить любую задачу по программированию
  • объяснить код
  • расставить комментарии в коде
  • и т.д
Попробуйте бесплатно

Оцени полезность:

12   голосов , оценка 4.083 из 5
Похожие ответы