在C或python中是否存在快速现成的最大基数二分匹配实现?
我试过了git branch|grep '^\s*temp'
,但速度很慢。我有一个两层图,每层有大约1000个节点。密度各不相同。什么时候我可以期待这个设置?
我看到这篇文章Fast max-flow min-cut library for Python,但有什么更快的吗?
答案 0 :(得分:0)
好吧,如果您打算使用网络流方法,那么所有可用的算法的时间复杂度似乎至少为O(|V||E|)
,或者大多数(例如O(|V|^2|E|)
)例。
如果您有一个包含2000个节点的图形,即使边数|E|
与顶点数|V|
呈线性关系,也会产生时间复杂度为O(|V|^2|E|)
的算法在平均每天的计算机中执行时间长达几分钟。如果图形密集,则| E |与|V|^2
呈线性关系,然后可能需要数天才能执行。
解决此二分最大匹配问题的替代算法可能是Hopcroft-Karp algorithm。它首先为二分匹配设置一个空集M
,然后通过在给定图中查找扩充路径来尝试展开M
。该算法具有O(|E|√|V|)
复杂度,优于Push Relabel或Edmonds-Karp等网络流量算法。
此外,已经有a Python library实施了Hopcroft-Karp算法,我相信这是你想要的另一件事。
答案 1 :(得分:0)
SciPy(自1.4.0版开始)包含scipy.sparse.csgraph.maximum_bipartite_matching
中Hopcroft-Karp的实现,与NetworkX相比具有优势。该功能也存在于以前的版本中,但随后假定与之完美匹配;在1.4.0中取消了这一假设。
它的精确程度将取决于二分图的结构,但是仅通过生成随机图(并忽略NetworkX初始化基础数据结构将花费的时间),我可以获得200倍的性能提升:>
import networkx as nx
from scipy.sparse import rand
from scipy.sparse.csgraph import maximum_bipartite_matching
n = 5000
graph = rand(n, n, density=.1, format='csr', random_state=42)
G = nx.algorithms.bipartite.from_biadjacency_matrix(graph)
>>> %timeit maximum_bipartite_matching(graph, perm_type='column')
8.95 ms ± 183 µs per loop (mean ± std. dev. of 7 runs, 100 loops each)
>>> %timeit nx.algorithms.bipartite.maximum_matching(G, top_nodes=range(n))
2.01 s ± 118 ms per loop (mean ± std. dev. of 7 runs, 1 loop each)