我正在尝试找到最有效的算法来查找多排列排列的给定排列的索引' 0'和' 1'。
Ex:给定{0,0,1,1}。所有可能的升序排列是:{0011,0101,0110,1001,1010,1100}。这些元素被索引为0 - > 6.给定s = 0110,结果为2.
这个问题与here非常相似,但他的问题是正确的设置(例如{1,2,3})。另一个类似的问题是here,但答案是O(N!)。以下代码是我的尝试,但也没有效率(O(N!))。
def find_index(s, pos): # s is the given permutation, pos is the index list of '1' in s
d_index = 0
c = 0
for i in range (len(pos)-1, -1, -1):
d_index = d_index + 1
if (len-1-pos[i] >= d_index):
c_i = c_i + Combination (d_index, len-1-pos[i])
if (c == 0):
return 0
return c
答案 0 :(得分:0)
这种方法简单地遍历所有二进制数,直到给定的数字为s,并检查每个数字是否具有所需的0和1的数量,如果确实如此,则递增计数器。
s = '0110' # input
count_0 = s.count('0')
count_1 = s.count('1')
l = len(s)
index = 0
for i in xrange(0, int(s,2)):
binary = ('{:0%sb}'%l).format(i) #converts integer into binary of length l bits
if binary.count('0') == count_0 and binary.count('1') == count_1: index += 1
答案 1 :(得分:0)
首先解决这个问题:给定一个多集,找到n
- 排列。你可以递归地做到这一点。让F(S, n)
成为计算两件事的函数:n
- 多集S
的排列和排列的总数。
`F(S, ~).total = F(S-{0}, ~).total + F(S-{1}, ~).total`.
如果F(S-{0}, ~).total < n
,F(S, n) = 0 . F(S-{0}, n)
别的F(S, n) = 1 . F(S-{1}, n - F(S-{0}, ~).total)
使用F(S, n)
,您可以进行二进制搜索,以查找所需排列的索引。此二进制搜索的范围为[0, N!]
。
让我们添加运行时:如果您的初始设置为S
且|S| = N
,则计算所有F(s, n)
s需要每个州O(N)
个时间,假设您正在记忆(这说明哈希州的状态可能不是O(1)
)。状态数为O(N*2^N)
。二进制搜索需要O(log N!) = O(N log N)
,运行时间为O(N*2^N)
。
答案 2 :(得分:0)
为什么不能使用列表?
s = '0110'
p = ['0011', '0101', '0110', '1001', '1010', '1100']
p.index(s)
为了使数据存储更加高效,您可以将它们用作整数:
s = 0b0110
p = [0b0011, 0b0101, 0b0110, 0b1001, 0b1010, 0b1100]
索引的工作方式相同。