python-拓扑排序解的个数

拓扑排序解的个数

给定有向无环图中所有边,计算图的拓扑排序解的个数。

输入

第一行为用例个数,后面每一行表示一个图中的所有边,边的起点和终点用空格隔开,边之间使用逗号隔开。

输出

拓扑排序解的个数。

输入样例

1
a c,b c,c d,d e,d f,e g,f g

输出样例

4

因为算法课需要,所以只好将别人代码进行翻译,暂时还没看懂原理。

代码基本来自对【ZJU 1346 Comparing Your Heroes 状态压缩DP 拓扑排序的计数】的翻译,因为网上对拓扑排序计数的资料太少,所以我暂时用python进行了改写。

需要对size进行修改,因为不知道输入判例会有多少种字母,size=26的话会TLE,size太小的话会RE,经过我的测试,size=13时,size最小且能AC,说明测试用例的字母种数为13。

def inputPre():
    global name, pre, m, n
    for i in range(m):
        v = 0
        u = 0
        while u < n:
            if p[i][0] == name[u]:
                break
            else:
                u += 1
        if u == n:
            name.append(p[i][0])
            n += 1
        while v < n:
            if p[i][1] == name[v]:
                break
            else:
                v += 1
        if v == n:
            name.append(p[i][1])
            n += 1
        pre[v] |= (1 << u)


def solve():
    global dp, n
    dp[0] = 1
    for s in range(1 << n):
        if dp[s] != 0:
            for i in range(n):
                if ((s & pre[i]) == pre[i]) and not (s & (1 << i)):
                    dp[s | (1 << i)] += dp[s]
    print(dp[(1 << n) - 1])


if __name__ == '__main__':
    N = int(input())
    for k in range(N):
        pairs = list(map(str, input().split(",")))  # 起点终点对集合
        m = len(pairs)
        n = 0
        p = []  # 存储起点终点对
        for i in range(m):
            pair = pairs[i].split()
            p.append(pair)
        name = []
        size = 13
        pre = [0 for i in range(size)]
        dp = [0 for i in range(1 << size)]
        inputPre()
        solve()

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值