Пересекающиеся выровненные квадраты (горизонт) - PullRequest
0 голосов
/ 16 марта 2020

Я программирую что-то похожее на проблему слияния горизонта. В моем случае я должен пересечь горизонты и не могу найти, что не так с моим кодом, он возвращает неправильные точки. Я использую алгоритм «разделяй и властвуй».

(_ Точка - это именованный кортеж, который содержит x (где изменяется высота) и ah (высота)) (_points - это список, содержащий все точки, которые образуют линия горизонта)

Один из примеров ввода может быть:

p1 = Skyline([(1,11,5),(2,6,7),(3,13,15)])
p2 = Skyline([(12,7,16),(2,6,7),(14,3,25),(19,18,22)])

И вывод p1 * p2 должен быть:

[Point(x=2, h=6), Point(x=7, h=0), Point(x=12, h=7), Point(x=15,h=0)]

Вот код:

def __mul__(self,sky1):
        """Returns a list of points resulting from the intersection of two skylines"""
        sky = []
        sky.extend(self._points)
        sky.extend(sky1._points)
        sorted(sky, key=attrgetter('x'))
        print("Skyline: points =", self._intersect(sky))
        return self._intersect(sky)


    def _intersect(self,sky):
        sky.sort(key=lambda tup: tup[0])
        """From a list of tuples, prints a list of points which gives the x and the h, when the h changes"""

        if sky==[]:
            return []
        if len(sky)==1:
            if isinstance(sky[0], self._Point):
                return [self._Point(x = sky[0][0], h = sky[0][1])]
            if isinstance(sky[0], tuple):
                return [self._Point(x = sky[0][0], h = sky[0][1]), self._Point(x = sky[0][2], h= 0)]

        mid=(len(sky)-1)//2
        left=self._intersect(sky[0:mid+1])
        right=self._intersect(sky[mid+1:])
        return self._inter(left,right)
 def _inter(self, right, left):
        #altures
        h1, h2 = 0, 0
        i, j = 0, 0
        _points = []
        self._points = _points
        formerh = 0

        while i < len(left) and j < len(right):
            #the building in the first group starts before
            if left[i][0] < right[j][0]:
                h2 = right[j][1]
                h1 = left[i][1]
                inici = right[j][0]
                j += 1
            #the other way round
            elif right[j][0] < left[i][0]:
                h1 = left[i][1]
                h2 = right[j][1]
                inici = left[i][0]
                i += 1
            #they both start at once
            else:
                h1 = left[i][1]
                h2 = right[j][1]
                inici = right[j][0]
                i += 1
                j += 1
            #if the new height is different from the former one, we add the point to our list
            if min(h1, h2) != formerh:
                formerh = min(h1,h2)
                self._points.append(self._Point(x = inici, h = min(h1, h2)))
        return self._points
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...