我有一个很大的数字,我需要在Python中拆分成较小的数字。我编写了以下代码来交换两者:
def split_number (num, part_size):
string = str(num)
string_size = len(string)
arr = []
pointer = 0
while pointer < string_size:
e = pointer + part_size
arr.append(int(string[pointer:e]))
pointer += part_size
return arr
def join_number(arr):
num = ""
for x in arr:
num += str(x)
return int(num)
但这个数字有所不同。很难调试,因为数字是如此之大,所以在我进入之前,我想我会在这里发布它,看看是否有更好的方法来做或者我是否遗漏了一些明显的东西。
非常感谢。
答案 0 :(得分:2)
显然,此操作无法保留“部件”中的任何前导0
。 join_number
无法接收part_size
参数,以便它可以使用所有前导零重建字符串格式吗?
没有发送者和接收者都知道的part_size
之类的信息,或者等效的信息(例如用于基于算术的类似分割和连接的基数,大致相当于{{1}根据你使用10**part_size
的方式,任务变得相当困难。如果接收者最初对此无能为力,为什么不将part_size
(或base等)作为发送和接收的part_size
列表中的第一个int放置?这样,编码通常变得“自给自足”,即不需要发送方和接收方都知道的任何补充参数。
答案 1 :(得分:2)
无需转换为字符串和字符串,这对于非常大的数字来说非常耗时
>>> def split_number(n, part_size):
... base = 10**part_size
... L = []
... while n:
... n,part = divmod(n,base)
... L.append(part)
... return L[::-1]
...
>>> def join_number(L, part_size):
... base = 10**part_size
... n = 0
... L = L[::-1]
... while L:
... n = n*base+L.pop()
... return n
...
>>> print split_number(1000005,3)
[1, 0, 5]
>>> print join_number([1,0,5],3)
1000005
>>>
在这里你可以看到只需将数字转换为str
所需的时间比我的整个功能要长!
>>> from time import time
>>> t=time();b = split_number(2**100000,3000);print time()-t
0.204252004623
>>> t=time();b = split_number(2**100000,30);print time()-t
0.486856222153
>>> t=time();b = str(2**100000);print time()-t
0.730905056
答案 2 :(得分:1)
您应该考虑将以下数字拆分为3个大小的块:
1000005 -> 100 000 5
你有两个问题。首先,如果你把那些整数放回去,你会得到:
100 0 5 -> 100005
(即,中间的一个是0,而不是000),这不是你开始的。第二个问题是你不确定最后一部分应该是多大。
我会确保您首先使用长度与零件尺寸完全相同的字符串,因此您知道完全每个零件应该有多大:
def split_number (num, part_size):
string = str(num)
string_size = len(string)
while string_size % part_size != 0:
string = "0%s"%(string)
string_size = string_size + 1
arr = []
pointer = 0
while pointer < string_size:
e = pointer + part_size
arr.append(int(string[pointer:e]))
pointer += part_size
return arr
其次,确保将每个部件的部件放回到正确的长度(确保您不会在前一部分放置前导零):
def join_number(arr, part_size):
fmt_str = "%%s%%0%dd"%(part_size)
num = arr[0]
for x in arr[1:]:
num = fmt_str%(num,int(x))
return int(num)
将所有这些结合起来,以下完整的程序:
#!/usr/bin/python
def split_number (num, part_size):
string = str(num)
string_size = len(string)
while string_size % part_size != 0:
string = "0%s"%(string)
string_size = string_size + 1
arr = []
pointer = 0
while pointer < string_size:
e = pointer + part_size
arr.append(int(string[pointer:e]))
pointer += part_size
return arr
def join_number(arr, part_size):
fmt_str = "%%s%%0%dd"%(part_size)
num = arr[0]
for x in arr[1:]:
num = fmt_str%(num,int(x))
return int(num)
x = 1000005
print x
y = split_number(x,3)
print y
z = join_number(y,3)
print z
产生输出:
1000005
[1, 0, 5]
1000005
表明它会一起回归。
请记住,我几年没有做过Python。几乎可以肯定有一种更“Pythonic”的方法来处理那些新奇的lambdas和事物(或者Python称之为),但是,由于你的代码是基本形式,我只回答了使其工作所需的最小变化。哦是的,并且要警惕负数: - )
答案 3 :(得分:0)
这是Alex Martelli回答的一些代码。
def digits(n, base):
while n:
yield n % base
n //= base
def split_number(n, part_size):
base = 10 ** part_size
return list(digits(n, base))
def join_number(digits, part_size):
base = 10 ** part_size
return sum(d * (base ** i) for i, d in enumerate(digits))