分治法(快包法)解決凸包問題,並使用matplotlib繪製凸包

這是算法設計課程學到分治法的一個作業,網上找了不少博客,但都沒咋看懂=_=(其實是因爲自己沒有認真去看),晚上吃過晚飯自己動手寫了寫,大約兩個小時後,它誕生了。

img
凸包的繪製是使用python中的matplotlib.pyplot庫實現的,也僅僅是爲了直觀和可視化,也爲了老師給更高的分數,誠然真正刷算法題還得是C++ or C

自己動動手,才發現真的很簡單,每次上方選面積最大的,下方選面積最小的畫線即可。

import random
import numpy
import matplotlib.pyplot as plt


def caculate(x1, y1, x2, y2, x3, y3):
    return x1 * y2 + x3 * y1 + x2 * y3 - x1 * y3 - x2 * y1 - x3 * y2


def findUpperMax(x1, y1, x2, y2, points):
    flag = False
    upperMax = 0
    upperx = uppery = 0
    for i in points:
        if i[0] == x1 and i[1] == y1 or i[0] == x2 and i[1] == y2:
            continue
        areaData = caculate(x1, y1, x2, y2, i[0], i[1])
        if areaData > 0:
            if areaData > upperMax:
                flag = True
                upperMax = areaData
                upperx = i[0]
                uppery = i[1]
    if flag == False:
        plt.plot([x1, x2], [y1, y2], color='r')
        plt.text(x1, y1 + 0.3, (x1, y1), ha='center', va='bottom', fontsize=10.5)
        plt.text(x2, y2 + 0.3, (x2, y2), ha='center', va='bottom', fontsize=10.5)
        return
    plt.plot([x1, upperx], [y1, uppery], color='k')
    plt.plot([x2, upperx], [y2, uppery], color='k')
    findUpperMax(x1, y1, upperx, uppery, points)
    findUpperMax(upperx, uppery, x2, y2, points)

def findBottomMin(x1, y1, x2, y2, points):
    flag = False
    lowerMax = 0
    lowerx = lowery = 0
    for i in points:
        if i[0] == x1 and i[1] == y1 or i[0] == x2 and i[1] == y2:
            continue
        areaData = caculate(x1, y1, x2, y2, i[0], i[1])
        if areaData < 0:
            if areaData < lowerMax:
                flag = True
                lowerMax = areaData
                lowerx = i[0]
                lowery = i[1]
    if flag == False:
        plt.plot([x1, x2], [y1, y2], color='r')
        plt.text(x1, y1 + 0.3, (x1, y1), ha='center', va='bottom', fontsize=10.5)
        plt.text(x2, y2 + 0.3, (x2, y2), ha='center', va='bottom', fontsize=10.5)
        return
    plt.plot([x1, lowerx], [y1, lowery], color='k')
    plt.plot([x2, lowerx], [y2, lowery], color='k')
    findBottomMin(x1, y1, lowerx, lowery, points)
    findBottomMin(lowerx, lowery, x2, y2, points)

#以下數值可以自行修改

pointsSize = 30  # 30個點
upper = 100  # 點的座標上限爲100
lower = -100  # 點的座標下限爲-100
xx = [random.randint(lower, upper) for i in range(pointsSize)]
yy = [random.randint(lower, upper) for i in range(pointsSize)]
points = []
for i in range(pointsSize):
    points.append([xx[i], yy[i]])
for i in range(0, pointsSize):
    plt.scatter(xx[i], yy[i], color='k', s=20)
points.sort(key=lambda x: (x[0], x[1]))
plt.plot([points[0][0], points[pointsSize - 1][0]], [points[0][1], points[pointsSize - 1][1]], color='k')
findUpperMax(points[0][0], points[0][1], points[pointsSize - 1][0], points[pointsSize - 1][1], points)
findBottomMin(points[0][0], points[0][1], points[pointsSize - 1][0], points[pointsSize - 1][1], points)
plt.show()

每次運行生成的點都在-100到+100之間,30個點,然後find answer

明天,一定解決最近對問題的分治法

^ ^另外,這是我第一篇用Markdown寫的筆記,紀念一hia hia hia hia~~~~


分割線,在底下發會兒二,大家不要介意~

哈拉澤空

哈拉澤空

啦啦啦啦

[My Blog]

(https://blog.csdn.net/weixin_43727229)

標題來啊來啊

ok


okk

okkk

okkkk


發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章