Форум программистов, компьютерный форум, киберфорум
Delphi для начинающих
Войти
Регистрация
Восстановить пароль
 
Рейтинг 4.86/37: Рейтинг темы: голосов - 37, средняя оценка - 4.86
0 / 0 / 0
Регистрация: 20.05.2009
Сообщений: 24
1

Задан треугольник с точкой, надо узнать, лежит ли точка в треугольнике или нет. Написать на делфи...

05.11.2009, 19:11. Просмотров 7220. Ответов 7
Метки нет (Все метки)


Лежит ли точка M(Xm,Ym) внутри треугольника, заданного координатами своих вершин A(Xa,Ya), B(Xb,Yb), C(Xc,Yc) на плоскости? Люди помогите с задачей, пожалуйста!

Добавлено через 1 минуту
Решите пожалуйста, до завтра надо

Добавлено через 7 минут
Решите пожалуйста, до завтра надо Для любой точки часто используют такой алгоритм.
1. Определяют длины сторон данного треугольника и треугольников, полученных из точки попарно с двумя вершинами треугольника,
2. Считают площади четырех треугольников.
Если сумма площадей трех "маленьких" треугольников равна(с учетом погрешности) площади данного треугольника, то точка внутри, иначе нет.

Добавлено через 1 минуту
Но как это все красиво оформить на делфи... И чтоб работало... Помогите пожалуйста
0
Programming
Эксперт
94731 / 64177 / 26122
Регистрация: 12.04.2006
Сообщений: 116,782
05.11.2009, 19:11
Ответы с готовыми решениями:

лежит ли точка в треугольнике??? или нет...
народ, помогите... вот задача... проверьте пожалуйса и исправьте... ошибку выдает при вычисление...

Определить лежит точка в треугольнике или нет
Даны координаты вершин треугольника и точка О(х,у). Определить лежит точка в треугольнике или нет.

Как узнать, лежит ли точка внутри триугольника или нет по заданным координатам.
дано координати точки А, и координати 3 сторон триугольника как узнать есть ли точка внутри...

Треугольник задан координатами вершин х 1 у1 х 2 у 2 х 3 у 3 точка а задана координатами х у требуется написать программу определяющую попадает ли указанная точка в заданный треугольник
Треугольник задан координатами вершин х 1 у1 х 2 у 2 х 3 у 3 точка а задана координатами х у...

7
13062 / 5848 / 1705
Регистрация: 19.09.2009
Сообщений: 8,807
05.11.2009, 21:20 2
Недавно делалась работа, где определение вхождения точки в треугольник применялось в качестве промежуточной задачи. Здесь работающий проект. Из него тебе нужно взять две функции: DotInTriangle() и GetAngleABC(). Для решения твоей задачи тебе нужно вызывать функцию DotInTriangle(). Сама же DotInTriangle() в своём теле вызывает GetAngleABC(). В этом решении площади не считаются - там применён другой (хоть и видимо похожий метод) - через подсчёт уголов.
0
13062 / 5848 / 1705
Регистрация: 19.09.2009
Сообщений: 8,807
05.11.2009, 22:25 3
Вот вариант по твоей задаче:
Delphi
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
unit Unit1;
 
interface
 
uses
  Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
  Dialogs, StdCtrls, ExtCtrls;
 
type
  TForm1 = class(TForm)
    Button1: TButton;
    Panel1: TPanel;
    Image1: TImage;
    procedure Button1Click(Sender: TObject);
  private
    { Private declarations }
  public
    { Public declarations }
  end;
 
  //Тип, задающий точку.
  TDot = record
    X         : Integer;
    Y         : Integer;
  end;
 
  //Тип, задающий треугольник (ABC).
  TTriangle = record
    A         : TDot;
    B         : TDot;
    C         : TDot;
    //Длина основания.
    Base      : Extended;
  end;
 
  //Тип массива для хранения равносторонних треугольников. Вид массива - динамический.
  TArrTriangle   = array of TTriangle;
  //Указатель на динамический массив треугольников.
  TPArrTriangle  = ^TArrTriangle;
 
const
  //Значение радиана (в градусах):
  Radian         : Extended = 180 / Pi;
  //Точность сравнения углов. В градусах.
  EpsilonAngle   : Extended = 0.001;
 
var
  Form1: TForm1;
 
implementation
 
uses Math;
 
{$R *.dfm}
 
//Рисование на канве.
 
//Рисует треугольник aTri на канве aCanvas.
//При прорисовке применяет масштаб aZoom.
procedure DrawTri(aCanvas : TCanvas; aZoom : Integer; aTri : TTriangle);
begin
  aCanvas.MoveTo(aTri.A.X * aZoom, aTri.A.Y * aZoom);
  aCanvas.LineTo(aTri.B.X * aZoom, aTri.B.Y * aZoom);
  aCanvas.LineTo(aTri.C.X * aZoom, aTri.C.Y * aZoom);
  aCanvas.LineTo(aTri.A.X * aZoom, aTri.A.Y * aZoom);
end;
 
//Рисует точку aDot на канве aCanvas.
//При прорисовке применяет масштаб aZoom.
procedure DrawDot(aCanvas : TCanvas; aZoom : Integer; aDot : TDot);
var
  DotZoom : TDot;
  Rect : TRect;
  LastPenStyle : TPenStyle;
begin
  //Точка с учётом масштаба.
  DotZoom.X := aDot.X * aZoom;
  DotZoom.Y := aDot.Y * aZoom;
 
  //Квадрат который будет изображать точку - чтобы сделать точку более крупной.
  //Это нужно для того чтобы точку было хорошо видно на канве.
  Rect.TopLeft.X      := DotZoom.X - 2;
  Rect.TopLeft.Y      := DotZoom.Y - 2;
  Rect.BottomRight.X  := DotZoom.X + 2;
  Rect.BottomRight.Y  := DotZoom.Y + 2;
  aCanvas.Rectangle(Rect);
 
  //Запоминаем текущий стиль пера.
  LastPenStyle := aCanvas.Pen.Style;
 
  //Устанавливаем стиль в виде пунктирных линий.
  aCanvas.Pen.Style := psDash;
 
  //Рисуем асимптоты.
  aCanvas.MoveTo(0, DotZoom.Y);
  aCanvas.LineTo(DotZoom.X, DotZoom.Y);
  aCanvas.MoveTo(DotZoom.X, 0);
  aCanvas.LineTo(DotZoom.X, DotZoom.Y);
 
  //Возвращаем предыдущий стиль пера.
  aCanvas.Pen.Style := LastPenStyle;
 
end;
 
//Вычисления.
 
//Возвращает значение угла ABC. (В градусах).
function GetAngleABC(aA, aB, aC : TDot) : Extended;
var
  LineBA    : Extended;
  LineBC    : Extended;
  LineAC    : Extended;
  CosABC    : Extended;
begin
 
  // Теорема косинусов:
  //AC^2 = BA^2 + BC^2 - 2*BA*BC*cosABC
  //-> cosABC = (AC^2 - BA^2 - BC^2)/2*BA*BC
  //-> ABC = ArcCos( cosABC ) - В радианах
  //-> ABC = ArcCos( cosABC ) * Radian - В градусах.
 
  LineBA := Sqrt( Sqr(aB.X - aA.X) + Sqr(aB.Y - aA.Y) );
  LineBC := Sqrt( Sqr(aB.X - aC.X) + Sqr(aB.Y - aC.Y) );
  LineAC := Sqrt( Sqr(aA.X - aC.X) + Sqr(aA.Y - aC.Y) );
 
  CosABC := ( - Sqr(LineAC) + Sqr(LineBA) + Sqr(LineBC) ) / ( 2 * LineBA * LineBC );
 
  //Так как функция ArcCos(CosABC) не определена для аргументов CosABC > 1 и CosABC < -1, а при
  //вычисленях с плавающей точкой возможны небольшие "заскоки" за область допустимых значений, то
  //такие случаи предусмотрим в коде.
  if CosABC > 1 then begin
    CosABC := 1;
  end else if CosABC < -1 then begin
    CosABC := -1;
  end;
 
  Result := Radian * ArcCos(CosABC);
 
end;
 
//Проверяет: попадает ли точка aDot внутрь треугольника aTri.
function DotInTriangle(aTri : TTriangle; aDot : TDot) : Boolean;
begin
  //Если точка D расположена внутри треугольника ABC, то выполнятся следующие 3 условия:
  //1. Углы: ABD + CBD = ABC
  //2. Углы: ACD + BCD = ACB
  //3. Углы: BAD + CAD = BAC
  //Если точка D расположена вне треугольника ABC, то какие-то два из трёх приведенных
  //выше условий будут нарушены таким образом:
  //1. Углы: ABD + CBD > ABC
  //2. Углы: ACD + BCD > ACB
  //3. Углы: BAD + CAD > BAC
  //Если при последовательной проверке трёх обнаружено первое нарушение -
  //это однозначно говорит о том, что точка D лежит за пределами треугольника ABC.
  //На этом и построим алгоритм.
  //
  //                     <A>
  //                     /|\
  //                    / | \
  //                   /  |  \
  //                  /   |   \
  //                 /    |    \
  //                /    <D>    \
  //               /   /     \   \
  //              /  /         \  \
  //             / /             \ \
  //            //                 \\
  //          <B>-------------------<C>
 
  Result := False;
 
  //Углы ABD, AСD, BAD неопределены, в случае, если точка D совпадает с любой
  //из вершин треугольника ABC. Поэтому предусмотрим этот случай.
  if
    ( (aTri.A.X = aDot.X) and (aTri.A.Y = aDot.Y) )
    or ( (aTri.B.X = aDot.X) and (aTri.B.Y = aDot.Y) )
    or ( (aTri.C.X = aDot.X) and (aTri.C.Y = aDot.Y) )
  then begin
    Result := True;
    Exit;
  end;
 
  //1. Если углы: ABD + CBD > ABC -> точка D за пределами треугольника.
  if
    Abs(
      GetAngleABC(aTri.A, aTri.B, aDot) + GetAngleABC(aTri.C, aTri.B, aDot)
      - GetAngleABC(aTri.A, aTri.B, aTri.C)
    ) > EpsilonAngle
  then begin
    Exit;
  end;
 
  //2. Если углы: ACD + BCD > ACB -> точка D за пределами треугольника.
  if
    Abs(
      GetAngleABC(aTri.A, aTri.C, aDot) + GetAngleABC(aTri.B, aTri.C, aDot)
      - GetAngleABC(aTri.A, aTri.C, aTri.B)
    ) > EpsilonAngle
  then begin
    Exit;
  end;
 
  //3. Если углы: BAD + CAD > BAC -> точка D за пределами треугольника.
  if
    Abs(
      GetAngleABC(aTri.B, aTri.A, aDot) + GetAngleABC(aTri.C, aTri.A, aDot)
      - GetAngleABC(aTri.B, aTri.A, aTri.C)
    ) > EpsilonAngle
  then begin
    Exit;
  end;
 
  //4. Точка D лежит внутри треугольника.
 
  Result := True;
end;
 
procedure TForm1.Button1Click(Sender: TObject);
var
  //Треугольник.
  Tri            : TTriangle;
  //Точка.
  Dot            : TDot;
begin
 
  Tri.A.X := 1;
  Tri.A.Y := 1;
  Tri.B.X := 1;
  Tri.B.Y := 10;
  Tri.C.X := 10;
  Tri.C.Y := 10;
 
  Dot.X := 3;
  Dot.Y := 5;
 
  //Рисуем точку.
  Image1.Canvas.Pen.Color := RGB(255, 0, 0);
  DrawDot(Image1.Canvas, 30, Dot);
 
  //Треугольник рисуем синим цветом.
  Image1.Canvas.Pen.Color := RGB(0, 0, 255);
  DrawTri(Image1.Canvas, 30, Tri);
 
  if DotInTriangle(Tri, Dot) then begin
    ShowMessage('Заданная точка лежит внутри треугольника');
  end else begin
    ShowMessage('Заданная точка не лежит внутри треугольника');
  end;
 
end;
 
end.
Только здесь координаты точек и координаты вершин треугольника задаются целыми числами. Если нужно вещественные - то там немного изменить код нужно.
Программа после вычислений сообщает о результате и выводит рисунок треугольника и точки на канву компонента TImage.
2
Миниатюры
Задан треугольник с точкой, надо узнать, лежит ли точка в треугольнике или нет. Написать на делфи...  
Вложения
Тип файла: rar Covers.rar (173.2 Кб, 130 просмотров)
0 / 0 / 0
Регистрация: 20.05.2009
Сообщений: 24
07.11.2009, 13:49  [ТС] 4
У меня есть вопрос, я не могу открыть на делфи это вложение... Появляются какие то иероглифы... Как правильно открыть файл? Подскажите пожалуйста...
0
13062 / 5848 / 1705
Регистрация: 19.09.2009
Сообщений: 8,807
07.11.2009, 14:37 5
Этот проект выполнен на Delphi 7. Я сейчас проверил - скачал архив Covers.rar, распаковал его, открыл проект - всё нормально открылось. И со шрифтами проблемы нет.
Сам архив нормально у тебя распаковался?
0
204 / 20 / 1
Регистрация: 29.10.2009
Сообщений: 430
08.11.2009, 16:36 6
Файл>Open Project>Тот самый проект
0
113 / 85 / 56
Регистрация: 09.01.2009
Сообщений: 209
08.11.2009, 17:25 7
Delphi
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
type Tpoint= record
    x:Integer;
    y:Integer;
    end;
var t:array [1..4] of tpoint;
    i:Integer;
    s1,s2,s3,s4:Real;
function s(x1,y1,x2,y2,x3,y3:real):Real;
var a,b,c,p:Real;
begin
a:=sqrt(sqr(x1-x2)+ sqr(y1-y2));
b:=sqrt(sqr(x2-x3)+ sqr(y2-y3));
c:=sqrt(sqr(x3-x1)+ sqr(y3-y1));
p:=(a+b+c)/2;
s:=Sqrt(p*(p-a)*(p-b)*(p-c));
end;
 
begin
 for i:=1 to 4 do
 begin
   Readln(t[i].x);
   Readln(t[i].y);
 end;
 s1:= s(t[1].x,t[1].y,t[2].x,t[2].y,t[3].x,t[3].y);
 s2:= s(t[4].x,t[4].y,t[2].x,t[2].y,t[3].x,t[3].y);
 s3:=s(t[1].x,t[1].y,t[4].x,t[4].y,t[3].x,t[3].y);
 s4:=s(t[1].x,t[1].y,t[2].x,t[2].y,t[4].x,t[4].y);
 
 if Abs(s1-(s2+s3+s4))<0.1 then writeln('Yes')
  else Writeln('no');
 readln;
end.
0
1 / 1 / 1
Регистрация: 03.10.2008
Сообщений: 35
08.11.2009, 22:30 8
Delphi
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
Function WherePoint(ax,ay,bx,by,px,py:real):integer;
var s :real;
begin
    s:=(bx-ax)*(py-ay)-(by-ay)*(px-ax);
    if s>0 then WherePoint:=1
    else if s<0 then WherePoint:=-1
    else WherePoint:=0;
end;
 
Function PointInsideTreangle(ax,ay,bx,by,cx,cy,px,py:real):boolean;
var s1,s2,s3 :integer;
begin
    PointInsideTreangle:=FALSE;
    s1:=WherePoint(ax,ay,bx,by,px,py);
    s2:=WherePoint(bx,by,cx,cy,px,py);
    if s2*s1<=0 then EXIT;
    s3:=WherePoint(cx,cy,ax,ay,px,py);
    if s3*s2<=0 then EXIT;
    PointInsideTreangle:=TRUE;
end;
 
Begin
   writeln(PointInsideTreangle(1,1,8,1,1,8,2,2)); {Inside}
   writeln(PointInsideTreangle(1,1,8,1,1,8,6,6)); {Outside}
End.
1
IT_Exp
Эксперт
87844 / 49110 / 22898
Регистрация: 17.06.2006
Сообщений: 92,604
08.11.2009, 22:30

Заказываю контрольные, курсовые, дипломные и любые другие студенческие работы здесь или здесь.

Определить: лежит точка в треугольнике
Мне уже два или три раза попадались задачи, где прямо или косвенно требовалось определить: лежит...

Лежит ли точка в круге и треугольнике
Даны круг и треугольник на плоскости.Кординаты вводятся с клавиатуры.Даны кординаты точки. Узнать...

Как узнать, лежит ли точка внутри эллипса или снаружи?
Как узнать лежить точка внутри эллипса или снаружи. Например имеем эллипс 8*x^2 + 5*y^5 = 77. Как...

Проверить лежит точка на отрезке или нет
Проверить лежит точка на отрезке или нет.

Найти лежит ли точка между кругами или нет
Ввести с клавиатуры радиус внутреннего и наружного круга R1 и R2 соответственно, и ввести...

Найти лежит ли точка внутри круга или нет
Получить радиус круга и координаты точки на плоскости (x, y) с клавиатуры. И вывести лежит ли точка...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
8
Ответ Создать тему
Опции темы

КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2021, vBulletin Solutions, Inc.