Найти углы треугольника, используя координаты {x, y}, а не по закону косинусов - PullRequest
0 голосов
/ 02 июня 2019

Я решаю эту задачу:

Вам даны длины для каждой стороны треугольника. Вам нужно найти все три угла для этого треугольника. Если заданная длина стороны не может сформировать треугольник (или сформировать вырожденный треугольник), то вы должны вернуть все углы как 0 (ноль).

Я уже решил это, используя закон косинусов , и теперь я пытаюсь использовать другой подход.

Идея заключается в следующем: поворачивать две стороны на один градус за раз, относительно обоих концов третьей стороны, и сохранять координаты и текущий угол в отдельных списках. Третья сторона используется как смещение по оси X для второй стороны. Затем выполняется проверка: оба списка имеют одинаковую координату? Если да - возможно построение треугольника с этих сторон.

Анимация вращения:

  • вращение происходит на 10 градусов за раз для демонстрации
  • E является точкой пересечения пути, если пересечение отсутствует, то треугольник невозможен.

enter image description here

Полученный треугольник:

enter image description here

Я написал решение Python, но оно не работает должным образом. Проблема в том, что координаты обеих сторон плохо совпадают, необходимо приближение.
Например: сторона вращения b до 90 °, координаты (0,0, 4,0), сторона вращения c до 127 °, координаты (- 0.009, 3.993), поэтому мне нужно сравнить эти координаты, используя приближение. В этом случае достаточно 0.01. Но в другом случае может потребоваться 0.1 или более, например a = 11, b = 20, c = 30. Я пытался адаптировать значение аппроксимации к размерам сторон, но без удачи.

Вопрос:

Как я могу рассчитать более точные координаты и почему мое решение не работает должным образом?


Решение Python:

#!/usr/bin/python3

from typing import List
from math import sin, cos, radians

def checkio(a: int, b: int, c: int) -> List[int]:

    def coords(side, side_offset):
        coord_list = []

        for degree in range(0,181):
            x = cos(radians(degree)) * side + side_offset
            y = sin(radians(degree)) * side

            coord_list.append((degree, x, y))

        return coord_list
    # make two lists with coordinates and degree, by rotating side "b" and side "c"
    b_coord_list = coords(b, 0) 
    # the side "a" is used just as an offset
    c_coord_list = coords(c, a) 

    for b_deg, b_x, b_y in b_coord_list:
        for c_deg, c_x, c_y in c_coord_list:

            # Approximate comparing
            if abs(b_x - c_x) <= 0.01 and abs(b_y - c_y) <= 0.01:
                l_angles = [b_deg, c_deg - b_deg, 180 - c_deg]
                l_angles.sort()

                # if all sides have angle, in other words if the triangle is possible
                if all(l_angles):
                    return sorted(l_angles)

    return [0, 0, 0]

### For testing:
#Good triangles
print(checkio(4, 4, 4))
print(checkio(3, 4, 5))
print(checkio(5, 4, 3))
print(checkio(11,20,30))
#Bad triangle
print(checkio(10, 20, 30))
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...