2.(图)-Kruskal算法

将图的各边按权值小到大排列,从最低权值开始建立最小成本生成树,如果造成回路则不使用此边,直到加入n-1个边。

比如对于如下图:

 按照权值排序边:

以B-C为最小边开始构造,然后是B-D,A-B,跳过C-D,加入B-F,D-E。

 加入了5条边,停止,最终生成最小成本树图形:

 

VERTS = 6


class edge:
    def __init__(self):
        self.start = 0
        self.to = 0
        self.find = 0
        self.val = 0
        self.next = None


v = [0] * (VERTS + 1)


def findmincost(head):
    minval = 100
    ptr = head
    # 遍历边
    while ptr != None:
        if ptr.val < minval and ptr.find == 0:
            minval = ptr.val
            retptr = ptr
        ptr = ptr.next
    retptr.find = 1
    return retptr


def mintree(head):
    global VERTS
    result = 0
    ptr = head
    for i in range(VERTS):
        v[i] = 0
    while ptr != None:
        mceptr = findmincost(head)
        v[mceptr.start] = v[mceptr.start] + 1
        v[mceptr.to] = v[mceptr.to] + 1
        if v[mceptr.start] > 1 and v[mceptr.to] > 1:
            v[mceptr.start] = v[mceptr.start] - 1
            v[mceptr.to] = v[mceptr.to] - 1
            result = 1
        else:
            result = 0
        if result == 0:
            print('start:[%d]->end:[%d]->value:[%d]' % (mceptr.start, mceptr.to, mceptr.val))
        ptr = ptr.next


data = [[1, 2, 6], [1, 6, 12], [1, 5, 10], [2, 3, 3],
        [2, 4, 5], [2, 6, 8], [3, 4, 7], [4, 6, 11],
        [4, 5, 9], [5, 6, 16]]
head = None
for i in range(len((data))):
    for j in range(1, VERTS):
        if data[i][0] == j:
            newnode = edge()
            newnode.start = data[i][0]
            newnode.to = data[i][1]
            newnode.val = data[i][2]
            if head == None:
                head = newnode
                head.next = None
                ptr = head
            else:
                ptr.next = newnode
                ptr = ptr.next
print('-----')
mintree(head)

 output:

start:[2]->end:[3]->value:[3]
start:[2]->end:[4]->value:[5]
start:[1]->end:[2]->value:[6]
start:[2]->end:[6]->value:[8]
start:[4]->end:[5]->value:[9]

原文地址:https://www.cnblogs.com/onenoteone/p/12441755.html