如果元组中的第二项是连续的,Python从元组中提取索引



我有一个由另一个列表中的一些项生成的元组列表。如果第二个元组项是连续的,我想在列表中获得索引(元组中的第一个项)。

。已处理列表

[(1, 'Chip 1'),
(1, 'Chip 2'),
(1, 'Chip 3'),
(2, 'Chip 4'),
(4, 'Chip 1'),
(4, 'Chip 2'),
(4, 'Chip 3'),
(4, 'Chip 4'),
(5, 'Chip 5'),
(7, 'Chip 1'),
(7, 'Chip 2'),
(7, 'Chip 3'),
(7, 'Chip 4'),
(8, 'Chip 5'),
(10, 'Chip 1'),
(10, 'Chip 2'),
(10, 'Chip 3'),
(12, 'Chip 1'),
(12, 'Chip 2'),
(14, 'Chip 1'),
(16, 'Chip 1'),
(16, 'Chip 2'),
(18, 'Chip 1'),
(18, 'Chip 2'),
(20, 'Chip 1'),
(20, 'Chip 2'),
(20, 'Chip 3'),
(20, 'Chip 4'),
(23, 'Chip 1'),
(25, 'Chip 1'),
(27, 'Chip 1'),
(27, 'Chip 2')]

我可以通过使用more_itertools获得顺序列表中的芯片,但我不知道如何进一步处理这个。有人能帮我弄明白吗?

import more_itertools as mit
chip_nums = [int(p[1][-1]) for p in processed]
for group in mit.consecutive_groups(chip_nums):
print(list(group))
[1, 2, 3, 4]
[1, 2, 3, 4, 5]
[1, 2, 3, 4, 5]
[1, 2, 3]
[1, 2]
[1]
[1, 2]
[1, 2]
[1, 2, 3, 4]
[1]
[1]
[1, 2]

groups包含processed列表中连续元素的索引(开始和结束,包括)
注:某些元组包含相同/相等的起始值和结束值,这表示没有连续性。

groups = []
start = 0
for i in range(len(processed) - 1):
if int(processed[i][1].split()[-1]) + 1 == int(
processed[i + 1][1].split()[-1]
):  # checks if the next element is 1 greater than previous element
pass
else:
groups.append((start, i))  # stores the start and ending index of a continuous group
start = i + 1
groups.append((start, i + 1))  # this handles the last remaining element
index_list = [[item[0] for item in processed[start : end + 1]] for start, end in groups]

输出:

[[1, 1, 1, 2], [4, 4, 4, 4, 5], [7, 7, 7, 7, 8], [10, 10, 10], [12, 12], [14], [16, 16], [18, 18], [20, 20, 20, 20], [23], [25], [27, 27]]

itertoolsoperator模块的队列:

from itertools import islice
from operator import itemgetter
import more_itertools as mit

it = iter(processed)
getter = itemgetter(0)
chip_nums = map(lambda x: int(x[1][-1]), processed)
for group in mit.consecutive_groups(chip_nums):
print([*islice(map(getter, it), len([*group]))])

输出:

[1, 1, 1, 2]
[4, 4, 4, 4, 5]
[7, 7, 7, 7, 8]
[10, 10, 10]
[12, 12]
[14]
[16, 16]
[18, 18]
[20, 20, 20, 20]
[23]
[25]
[27, 27]

你可以这样做:

(您将在该代码后找到解释)

from itertools import groupby
from operator import itemgetter
# PART 1
# List that will contain lists of indexes of "chip_nums". 
# Each list of indexes will correspond to consecutive chips values
list_of_indexes =list()
for k,g in groupby(enumerate(chip_nums),lambda x:x[0]-x[1]):
group = (map(itemgetter(0),g))
group = list(map(int,group))
list_of_indexes.append(group)

# PART 2
# From the retrieved indexes, get fist value in tuple ("index in tuple")
list_of_indexes_contained_in_tuples = list()
for indexes in list_of_indexes:
consecutive_indexes = list()
for index in indexes:
tuple_in_processed = processed[index]
index_in_tuple = tuple_in_processed[0]
consecutive_indexes.append(index_in_tuple)
list_of_indexes_contained_in_tuples.append(consecutive_indexes)

print(list_of_indexes_contained_in_tuples)

输出:

[[1, 1, 1, 2], [4, 4, 4, 4, 5], [7, 7, 7, 7, 8], [10, 10, 10], [12, 12], [14], [16, 16], [18, 18], [20, 20, 20, 20], [23], [25], [27, 27]]

解释:

PART 1"是more_itertools函数consecutive_groups的修改版本。我不知道你是否知道,consecutive_groups(https://github.com/more-itertools/more-itertools/blob/master/more_itertools/more.py)的源代码是这个配方的实现,可以在Python.org上找到:https://docs.python.org/2.6/library/itertools.html#examples

这个配方最初是在Python 2.6中编写的:

from operator import itemgetter
from itertools import groupby
data = [2, 3, 4, 5, 12, 13, 14, 15, 16, 17]
for k, g in groupby(enumerate(data), lambda (i,x):i-x):
print map(itemgetter(1), g)

在Python 3中转置,你将得到:

from operator import itemgetter
from itertools import groupby
data = [2, 3, 4, 5, 12, 13, 14, 15, 16, 17]
for k, g in groupby(enumerate(data), lambda x:x[0]-x[1]):
print(list(map(itemgetter(1), g)))

该修改包括对Python 3的lambda函数的改编。注意,我们还用list()包装了map函数,以便获得列表对象而不是map对象。

到目前为止,使用这个函数,我们得到了您使用您提供的代码得到的结果。

输出:

[2, 3, 4, 5]
[12, 13, 14, 15, 16, 17]

现在,我们将修改这个函数,以便获得元素的索引,而不是列表中的值(这里称为"data")。为此,我们只需要将0作为参数传递给itemgetter,而不是1:

data = [2, 3, 4, 5, 12, 13, 14, 15, 16, 17]
for k, g in groupby(enumerate(data), lambda x:x[0]-x[1]):
print(list(map(itemgetter(0), g)))

不,我们有索引。

输出:

[0, 1, 2, 3]
[4, 5, 6, 7, 8, 9]

第二部分只是使用索引来获取元组中的第一个项(也就是您想要的索引)。

因此,简而言之,我从more_itertools中改编了原始函数consecutive_groups,以便返回项的索引而不是它们的值,并使用这些索引来检索每个元组中的第一个值。

最新更新