Python 将整数列表分解为递增序列列表
假设列表中没有连续整数 我曾尝试使用NumPy(Python 将整数列表分解为递增序列列表,python,Python,假设列表中没有连续整数 我曾尝试使用NumPy(np.diff)来表示每个元素之间的差异,但未能使用它来获得答案。下面是输入(第一行)和预期输出(第二行)的两个示例 [6, 0, 4, 8, 7, 6] [[6], [0, 4, 8], [7], [6]] [1, 4, 1, 2, 4, 3, 5, 4, 0] [[1, 4], [1, 2, 4], [3, 5], [4], [0]] 只是因为我感觉亲切,这也适用于负数 seq = [6, 0, 4, 8, 7, 6] seq_by_in
np.diff
)来表示每个元素之间的差异,但未能使用它来获得答案。下面是输入(第一行)和预期输出(第二行)的两个示例
[6, 0, 4, 8, 7, 6]
[[6], [0, 4, 8], [7], [6]]
[1, 4, 1, 2, 4, 3, 5, 4, 0]
[[1, 4], [1, 2, 4], [3, 5], [4], [0]]
只是因为我感觉亲切,这也适用于负数
seq = [6, 0, 4, 8, 7, 6]
seq_by_incr_groups = [] # Will hold the result
incr_seq = [] # Needed to create groups of increasing values.
previous_value = 0 # Needed to assert whether or not it's an increasing value.
for curr_value in seq: # Iterate over the list
if curr_value > previous_value: # It's an increasing value and belongs to the group of increasing values.
incr_seq.append(curr_value)
else: # It was lower, lets append the previous group of increasing values to the result and reset the group so that we can create a new one.
if incr_seq: # It could be that it's empty, in the case that the first number in the input list is a negative.
seq_by_incr_groups.append(incr_seq)
incr_seq = []
incr_seq.append(curr_value)
previous_value = curr_value # Needed so that we in the next iteration can assert that the value is increasing compared to the prior one.
if incr_seq: # Check if we have to add any more increasing number groups.
seq_by_incr_groups.append(incr_seq) # Add them.
print(seq_by_incr_groups)
以下是一种简单的方法,可以在不使用任何额外库的情况下完成您的要求:
result_list = []
sublist = []
previous_number = None
for current_number in inp:
if previous_number is None or current_number > previous_number:
# still ascending, add to the current sublist
sublist.append(current_number)
else:
# no longer ascending, add the current sublist
result_list.append(sublist)
# start a new sublist
sublist = [current_number]
previous_number = current_number
if sublist:
# add the last sublist, if there's anything there
result_list.append(sublist)
你可以写一个简单的
脚本
,就我理解你的问题陈述而言,你不需要numpy
。尝试下面的脚本。我已经在我的Ubuntu机器上使用Python3.6.7
和Python2.7.15+
对它进行了测试
def breakIntoList(inp):
if not inp:
return []
sublist = [inp[0]]
output = []
for a in inp[1:]:
if a > sublist[-1]:
sublist.append(a)
else:
output.append(sublist);
sublist = [a]
output.append(sublist)
return output
list = [1, 4, 1, 2, 4, 3, 5, 4, 0]
print(list)
print(breakIntoList(list))
说明:
脚本首先检查传递给它的输入列表是否有一个或多个元素
然后初始化一个子列表(变量名
),以按递增顺序保存元素。之后,我们将输入列表的第一个元素附加到子列表中
我们从输入列表的第二个元素(Index:1
)开始迭代输入列表。我们继续检查输入列表中的当前元素是否大于子列表的最后一个元素(通过子列表[-1]
)。如果是,我们将当前元素附加到子列表(在末尾)。否则,这意味着我们不能在子列表中保留当前元素。我们将子列表附加到输出列表,清除子列表(用于保存其他递增顺序子列表),并将当前元素添加到子列表中
最后,我们将剩余的子列表附加到输出列表中
下面的代码应该对您有所帮助。不过,我建议您使用适当的术语,并考虑处理角情况:
li1 = [6, 0, 4, 8, 7, 6]
li2 = [1, 4, 1, 2, 4, 3, 5, 4, 0]
def inc_seq(li1):
lix = []
li_t = []
for i in range(len(li1)):
#print (i)
if i < (len(li1) - 1) and li1[i] >= li1[i + 1]:
li_t.append(li1[i])
lix.append(li_t)
li_t = []
else:
li_t.append(li1[i])
print (lix)
inc_seq(li1)
inc_seq(li2)
li1=[6,0,4,8,7,6]
li2=[1,4,1,2,4,3,5,4,0]
def公司(li1):
lix=[]
li_t=[]
对于范围内的i(len(li1)):
#印刷品(一)
如果i<(len(li1)-1)和li1[i]>=li1[i+1]:
li_t.追加(li1[i])
lix.append(li\u t)
li_t=[]
其他:
li_t.追加(li1[i])
打印(lix)
公司序号(li1)
公司序号(li2)
这里有一个使用dict、列表理解和zip的替代方法:
seq = [1, 4, 1, 2, 4, 3, 5, 4, 0]
dict_seq = {i:j for i,j in enumerate(seq)}
# Get the index where numbers start to decrease
idx = [0] # Adding a zero seems counter-intuitive now; we'll see the benefit later.
for k, v in dict_seq.items():
if k>0:
if dict_seq[k]<dict_seq[k-1]:
idx.append(k)
# Using zip, slice and handling the last entry
inc_seq = [seq[i:j] for i, j in zip(idx, idx[1:])] + [seq[idx[-1:]]]
通过启动idx=[0]
并创建两个子列表idx
,idx[1:]
,我们可以zip
这些子列表形成[0:2],[2:5],[5:7]和[7:8]
,并具有列表理解能力
>>> print(idx)
>>> [0, 2, 5, 7, 8]
>>> for i, j in zip(idx, idx[1:]):
print('[{}:{}]'.format(i,j))
[0:2]
[2:5]
[5:7]
[7:8] # <-- need to add the last slide [8:]
打印(idx)
>>> [0, 2, 5, 7, 8]
>>>对于zip中的i,j(idx,idx[1:]):
打印('[{}:{}]'.格式(i,j))
[0:2]
[2:5]
[5:7]
[7:8]#您可以使用启用列表中顺序元素对的迭代以及枚举
来跟踪序列不增加的索引值,以便将相应的片段附加到输出列表中
from itertools import zip_longest
nums = [1, 4, 1, 2, 4, 3, 5, 4, 0]
results = []
start = 0
for i, (a, b) in enumerate(zip_longest(nums, nums[1:])):
if b is None or b <= a:
results.append(nums[start:i+1])
start = i + 1
print(results)
# [[1, 4], [1, 2, 4], [3, 5], [4], [0]]
从itertools导入zip\u
nums=[1,4,1,2,4,3,5,4,0]
结果=[]
开始=0
对于枚举中的i,(a,b)(zip_longest(nums,nums[1:]):
如果b是无或b,这就是你想要的吗@NiklasNoem我认为这与OP所期待的正好相反不。完全不同的问题。您应该包括您尝试过的内容。这将立即抛出一个TypeError
,因为您无法将None
与int
进行比较。当我在python 2或3My中运行它时,它不会为我抛出一个TypeError。很糟糕,我有一个糟糕的测试用例。这在python2中运行。我会更新,如果你编辑使其工作,我一定会删除向下:)从一个向下到一个向上!很好,很干净对不起,我想知道我是否应该写任何答案,因为我确信任何时候都会有答案。这是最有吸引力的方式,比我的方法更好!如果输入列表中有0,则此操作无效<代码>非b
应该是b为无
@alexbclay-感谢您指出这一点。相应地编辑答案(如果需要,现在可以正确处理包含负数的问题)。
from itertools import zip_longest
nums = [1, 4, 1, 2, 4, 3, 5, 4, 0]
results = []
start = 0
for i, (a, b) in enumerate(zip_longest(nums, nums[1:])):
if b is None or b <= a:
results.append(nums[start:i+1])
start = i + 1
print(results)
# [[1, 4], [1, 2, 4], [3, 5], [4], [0]]