我正在尝试将一些因子编码为离散数,然后将离散数反向工程回为其因子-但是一旦我添加了足够的因子,反向过程就不会显示正确的数字。
a = 3
b = 13
c = 7
d = 8
e = 3
f = 2
state = (((((b)*20+c)*10+d)*10+e)*5+f)*5
# If i add "a*4" to the front of the line (as shown in this line below), A and B is no longer showing correct
state = ((((((a)*4+b)*20+c)*10+d)*10+e)*5+f)*5
print(state)
print("f:", state // 5 % 5)
state = state // 5
print(state)
print("e:", state // 5 % 5)
state = state // 5
print(state)
print("d:", state // 10 % 10)
state = state // 10
print(state)
print("c:", state // 10 % 10)
state = state // 10
print(state)
print("b:", state // 20 % 20)
state = state // 20
print(state)
print("a:", state // 4 % 4)
state = state // 4
print(state)
答案 0 :(得分:2)
您正在尝试做一些不可能的事情。如果您定义
def make_state(a,b,c,d,e,f):
return ((((((a)*4+b)*20+c)*10+d)*10+e)*5+f)*5
然后make_state(3,13,7,8,3,2)
和make_state(4,9,7,8,3,2)
的计算结果相同(1269585)。因此,不可能从1269585开始并将该数字解码回原始向量。 make_state()
不是一对一的。它会丢失信息。较小的计算state = (((((b)*20+c)*10+d)*10+e)*5+f)*5
也会丢失信息(至少对所记录的矢量没有严格的限制)。通常,对于任何整数x
,函数f(a,b): return ax+b
都不是一对一的,因此,除非我有所遗漏,否则整个用于编码数字序列的方法都是不可能的。>
另一方面,如果数字的上限是已知的,则您可以执行类似的操作。例如,如果a,b,c,d,e,f
是分别小于4,20,10,10,5,5
的非负整数,则函数
def encode(a,b,c,d,e,f):
return 5*(5*(10*(10*(20*a+b)+c)+d)+e)+f
可以反转。这来自division algorithm,该声明指出对于a,b
与b > 0
的任何整数,a
可以唯一地以{{1}的形式编写}和a = b*q + r
。在上述功能中,0 <= r < b
中的 可以通过除以f
来唯一地恢复,{{1}中5
中的部分也可以}。从那里您可以恢复()
,依此类推。一系列5 5*( ... ) + f
就足够了。请注意,e
的边界不会进入计算。
要解码:
divmods
例如:
a
更一般地:
def decode(n):
q,f = divmod(n,5)
q,e = divmod(q,5)
q,d = divmod(q,10)
q,c = divmod(q,10)
a,b = divmod(q,20)
return a,b,c,d,e,f
工作原理如下:
>>> encode(3,13,7,8,3,2)
184467
>>> decode(184467)
(3, 13, 7, 8, 3, 2)