def test_g73_trian_lower(self): Figure.rectangle = Rectangle() # Сразу создаем прямоугольник # Сначала делаем отрезок t = Segment(R2Point(-1.0, -1.0), R2Point(1.0, 1.0)) # Соединяем с третьей точкой -> Получаем треугольник t = t.add(R2Point(1.0, -1.0)) assert t.g73() == approx(2.0)
def test_g73_rect_x_lay_trian_up1(self): # Сразу создаем прямоугольник Figure.rectangle = Rectangle(R2Point(0.0, 0.0), R2Point(2.0, 1.0)) t = Point(R2Point(0.0, 2.0)) t = t.add(R2Point(2.0, 0.0)) t = t.add(R2Point(2.0, 2.0)) # Общая площадь должна быть 0.5 (четверть прямоугольника) assert t.g73() == approx(0.5)
def test_g73_rect_x_lay_trian_trian_throught_border_three(self): # Сразу создаем прямоугольник Figure.rectangle = Rectangle(R2Point(0.0, 0.0), R2Point(2.0, 1.0)) t = Point(R2Point(1.0, 0.0)) t = t.add(R2Point(1.0, 1.0)) t = t.add(R2Point(3.0, 2.0)) # Общая площадь должна быть 0.5 assert t.g73() == approx(0.5)
def test_g73_trian_big_upper(self): Figure.rectangle = Rectangle() # Сразу создаем прямоугольник # Сначала делаем отрезок t = Point(R2Point(-2.0, 2.0)) t = t.add(R2Point(-2.0, -2.0)) # Соединяем с третьей точкой -> Получаем большой треугольник t = t.add(R2Point(2.0, 2.0)) # Общая площадь должна быть 2 (половина квадрата) assert t.g73() == approx(2.0)
def test_g73_the_same_square(self): Figure.rectangle = Rectangle() # Сразу создаем прямоугольник # Сначала делаем отрезок t = Segment(R2Point(-1.0, -1.0), R2Point(1.0, -1.0)) # Соединяем с третьей точкой -> Получаем треугольник t = t.add(R2Point(1.0, 1.0)) # Соединяем с четвертой точкой -> Получаем квадрат (точки совпадают с вершинам "прямоугольника" по умолчанию) t = t.add(R2Point(-1.0, 1.0)) assert t.g73() == approx(4.0)
def test_g73_small_square_in(self): Figure.rectangle = Rectangle() # Сразу создаем прямоугольник # Сначала делаем отрезок t = Segment(R2Point(-0.5, -0.5), R2Point(0.5, -0.5)) # Соединяем с третьей точкой -> Получаем треугольник t = t.add(R2Point(0.5, 0.5)) # Соединяем с четвертой точкой -> Получаем маленький квадратик внутри нашего "прямоугольника" t = t.add(R2Point(-0.5, 0.5)) # Общая площадь равна площади всей замкнутой оболочки, т.е. единицы (всего квадратика) assert t.g73() == approx(1.0)
def test_g73_line_up(self): Figure.rectangle = Rectangle() # Сразу создаем прямоугольник # Сначала делаем отрезок t = Segment(R2Point(-1.0, 0.5), R2Point(1.0, 0.5)) # Соединяем с третьей точкой -> Получаем треугольник t = t.add(R2Point(1.0, 1.0)) # Соединяем с четвертой точкой -> Получаем полосочку вверху нашего квадрата t = t.add(R2Point(-1.0, 1.0)) # Общая площадь равна площади полоски, т.е. тоже единица assert t.g73() == approx(1.0)
def test_g6(self): t = Segment(R2Point(-1.0, 0.0), R2Point(1.0, 0.0)) t = t.add(R2Point(0.0, 1.0)) t = t.add(R2Point(0.0, -1.0)) t = t.add(R2Point(1.0, 1.0)) t = t.add(R2Point(1.0, -1.0)) t = t.add(R2Point(-1.0, 1.0)) t = t.add(R2Point(-1.0, -1.0)) t = t.add(R2Point(3.0, -1.0)) t = t.add(R2Point(-1.0, 3.0)) assert t.g() == approx(sqrt(2.0) + 2 * sqrt(10.0))
def setup_method(self): Figure.rectangle = Rectangle() # Сразу создаем прямоугольник self.f = Polygon( R2Point( 0.0, 0.0), R2Point( 1.0, 0.0), R2Point( 0.0, 1.0) ) Figure.fixed_point = R2Point(0.0, 0.0)
def test_g73_not_crossing(self): Figure.rectangle = Rectangle() # Сразу создаем прямоугольник # Сначала делаем отрезок t = Point(R2Point(-1.0, 2.0)) t = t.add(R2Point(1.0, 2.0)) # Соединяем с третьей точкой -> Получаем треугольник t = t.add(R2Point(1.0, 3.0)) # Соединяем с четвертой точкой -> Получаем полосочку ВЫШЕ нашего квадрата и не пересекающего его t = t.add(R2Point(-1.0, 3.0)) # Общая площадь равна площади полоски, т.е. тоже единица assert t.g73() == 0.0
def test_g73_x_elongated(self): Figure.rectangle = Rectangle() # Сразу создаем прямоугольник # Сначала делаем отрезок t = Point(R2Point(-2.0, -1.0)) t = t.add(R2Point(2.0, -1.0)) # Соединяем с третьей точкой -> Получаем треугольник t = t.add(R2Point(2.0, 1.0)) # Соединяем с четвертой точкой -> Получаем вытянутый прямоугольник t = t.add(R2Point(-2.0, 1.0)) # Но общая-то площадь измениться всё-равно не должна assert t.g73() == approx(4.0)
def test_g73_rect_x_lay_same_line2(self): # Сразу создаем прямоугольник Figure.rectangle = Rectangle(R2Point(-1.0, 0.0), R2Point(2.0, 1.0)) t = Point(R2Point(1.0, 1.0)) t = t.add(R2Point(2.0, 2.0)) t = t.add(R2Point(0.0, 2.0)) t = t.add(R2Point(2.0, 1.0)) t = t.add(R2Point(0.0, 2.0)) t = t.add(R2Point(0.0, 1.0)) t = t.add(R2Point(-1.0, 2.0)) t = t.add(R2Point(-1.0, 1.0)) # Общая площадь должна быть 0.0 (пересечения лишь по верхней границе) assert t.g73() == 0.0
def test_vertexes4(self): assert self.f.add( R2Point( 0.4, 1.0)).add( R2Point( 1.0, 0.4)).add( R2Point( 0.8, 0.9)).add( R2Point( 0.9, 0.8)).points.size() == 7 assert self.f.add(R2Point(2.0, 2.0)).points.size() == 4
def test_g73_trian_upper(self): Figure.rectangle = Rectangle() # Сразу создаем прямоугольник # Сначала делаем отрезок t = Polygon( R2Point( -1.0, -1.0), R2Point( 1.0, 1.0), R2Point( -1.0, 1.0) ) # t = Point(R2Point(-1.0, -1.0)) # t = t.add(R2Point(1.0, 1.0)) # t = t.add(R2Point(-1.0, 1.0)) assert t.g73() == approx(2.0)
def test_g4(self): t = Segment(R2Point(-1.0, 0.0), R2Point(1.0, 0.0)) t = t.add(R2Point(0.0, 1.0)) t = t.add(R2Point(0.0, -1.0)) t = t.add(R2Point(1.0, 1.0)) t = t.add(R2Point(1.0, -1.0)) t = t.add(R2Point(-1.0, 1.0)) t = t.add(R2Point(-1.0, -1.0)) assert t.g() == approx(4.0 * sqrt(2.0))
def add(self, t): # поиск освещённого ребра for n in range(self.points.size()): if t.is_light(self.points.last(), self.points.first()): break self.points.push_last(self.points.pop_first()) # хотя бы одно освещённое ребро есть if t.is_light(self.points.last(), self.points.first()): # учёт удаления ребра, соединяющего конец и начало дека self._perimeter -= float(self.points.first().dist( self.points.last())) self._g -= support.lenght(self.points.first(), self.points.last()) self._area += abs( R2Point.area(t, self.points.last(), self.points.first())) # удаление освещённых рёбер из начала дека p = self.points.pop_first() while t.is_light(p, self.points.first()): self._g -= support.lenght(p, self.points.first()) self._perimeter -= float(p.dist(self.points.first())) self._area += abs(R2Point.area(t, p, self.points.first())) p = self.points.pop_first() self.points.push_first(p) # удаление освещённых рёбер из конца дека p = self.points.pop_last() while t.is_light(self.points.last(), p): self._g -= support.lenght(p, self.points.last()) self._perimeter -= float(p.dist(self.points.last())) self._area += abs(R2Point.area(t, p, self.points.last())) p = self.points.pop_last() self.points.push_last(p) # добавление двух новых рёбер self._perimeter += float( t.dist(self.points.first()) + t.dist(self.points.last())) self._g += \ support.lenght(t, self. points.first()) + support.lenght(t, self. points.last()) self.points.push_first(t) return self
def add(self, r): if R2Point.is_triangle(self.p, self.q, r): return Polygon(self.p, self.q, r) elif self.q.is_inside(self.p, r): return Segment(self.p, r) elif self.p.is_inside(r, self.q): return Segment(r, self.q) else: return self
def __init__(self, a, b, c): self.points = Deq() self.points.push_first(b) if b.is_light(a, c): self.points.push_first(a) self.points.push_last(c) else: self.points.push_last(a) self.points.push_first(c) self._perimeter = a.dist(b) + b.dist(c) + c.dist(a) self._area = abs(R2Point.area(a, b, c))
def add(self, r): if R2Point.is_triangle(self.p, self.q, r): return Polygon(self.p, self.q, r) elif self.q.is_inside(self.p, r): self.rectangle.add_crossing( self.p, r) # Проверяем, пересекает ли отрезок какую-либо из граней return Segment(self.p, r) elif self.p.is_inside(r, self.q): self.rectangle.add_crossing( r, self.q ) # Проверяем, пересекает ли отрезок какую-либо из граней return Segment(r, self.q) else: return self
def __init__(self, a, b, c): self.points = Deq() self.points.push_first(b) if b.is_light(a, c): self.points.push_first(a) self.points.push_last(c) else: self.points.push_last(a) self.points.push_first(c) self._perimeter = a.dist(b) + b.dist(c) + c.dist(a) self._area = abs(R2Point.area(a, b, c)) # подсчет велины g которая включает сумму искомых нами сегментов self._g = support.lenght(a, b) + support.lenght(b, c) \ + support.lenght(c, a)
class Figure: """ Абстрактная фигура """ fixed_point = R2Point(0.0, 0.0) rectangle = Rectangle() def perimeter(self): return 0.0 def area(self): return 0.0 def g(self): return None def g73(self): """ По умолчанию площадь пересечения равна нулю """ return 0.0
def __init__(self, a, b, c): self.points = Deq() self.points.push_first(b) if b.is_light(a, c): self.points.push_first(a) self.points.push_last(c) else: self.points.push_last(a) self.points.push_first(c) self._perimeter = a.dist(b) + b.dist(c) + c.dist(a) self._area = abs(R2Point.area(a, b, c)) self._g = a.dist(self.fixed_point) + b.dist(self.fixed_point) + \ c.dist(self.fixed_point) self.rectangle.add_crossing( b, c) # Проверяем, пересекает ли отрезок какую-либо из граней self.rectangle.add_crossing( b, a) # Проверяем, пересекает ли отрезок какую-либо из граней self.rectangle.add_crossing( a, c) # Проверяем, пересекает ли отрезок какую-либо из граней # Добавляем в Дек вершины прямоугольника, которые находятся внутри выпуклой оболочки, # чтобы корректно считать площадь, если НЕТ пересечения self.rectangle.add_inside(a, b, c)
#!/usr/bin/env -S python3 -B from r2point import R2Point from convex import Figure, Void print("Заданная точка") Figure.fixed_point = R2Point() print("\nТочки плоскости") f = Void() try: while True: f = f.add(R2Point()) print(f"S = {f.area()}, P = {f.perimeter()}, g = {f.g()}") print() except(EOFError, KeyboardInterrupt): print("\nStop")
def test_add1(self): assert self.f.add(R2Point(0.0, 0.0)) is self.f
def test_add(self): assert isinstance(self.f.add(R2Point(0.0, 0.0)), Point)
# удаление освещённых рёбер из конца дека p = self.points.pop_last() while t.is_light(self.points.last(), p): self._g -= support.lenght(p, self.points.last()) self._perimeter -= float(p.dist(self.points.last())) self._area += abs(R2Point.area(t, p, self.points.last())) p = self.points.pop_last() self.points.push_last(p) # добавление двух новых рёбер self._perimeter += float( t.dist(self.points.first()) + t.dist(self.points.last())) self._g += \ support.lenght(t, self. points.first()) + support.lenght(t, self. points.last()) self.points.push_first(t) return self if __name__ == "__main__": f = Void() print(type(f), f.__dict__) f = f.add(R2Point(0.0, 0.0)) print(type(f), f.__dict__) f = f.add(R2Point(1.0, 0.0)) print(type(f), f.__dict__) f = f.add(R2Point(0.0, 1.0)) print(type(f), f.__dict__)
def add_pt(f, x=None, y=None): f = f.add(R2Point(x, y)) print(f"S = {f.area()}, P = {f.perimeter()}, g73 = {f.g73()}\n") return f
#!/usr/bin/env -S python3 -B from convex import Void from r2point import R2Point # print("Старое задание: Заданная точка") # Figure.fixed_point = R2Point(0.0, 0.0) print("Задание #73 (Сальдиков): Вершина #1 правильного прямоугольника") #vertex1 = R2Point(0.0, 0.0) vertex1 = R2Point() print( "Задание #73 (Сальдиков): Вершина #2 (противоположная) правильного прямоугольника" ) #vertex2 = R2Point(2.0, 1.0) vertex2 = R2Point() def add_pt(f, x=None, y=None): f = f.add(R2Point(x, y)) print(f"S = {f.area()}, P = {f.perimeter()}, g73 = {f.g73()}\n") return f print("\nТочки плоскости") f = Void(vertex1, vertex2) try: # f = add_pt(f, 1.0, 1.0) # f = add_pt(f, 2.0, 2.0) # f = add_pt(f, 0.0, 2.0) # f = add_pt(f, 2.0, 1.0)
def setup_method(self): self.f = Segment(R2Point(0.0, 0.0), R2Point(1.0, 0.0)) Figure.fixed_point = R2Point(0.5, 0.0)
def test_add2(self): assert isinstance(self.f.add(R2Point(1.0, 0.0)), Segment)