pandas 如何基于列值从 Dataframe 创建列表对象?

kb5ga3dv  于 2023-05-05  发布在  其他
关注(0)|答案(3)|浏览(161)

对于下面的df,如何创建下面所需的输出?我特别需要一个元组列表的列表。

import pandas as pd
df = pd.DataFrame({'x':['ab_c_1.0.0','ab_c_1.0.1','ab_c_1.0.2','ab_c_1.1.0','ab_c_1.1.1','ab_c_1.2.0','ab_c_1.3.0','ab_c_1.3.1'],
                   'y':['a','b','c','d','e','f','g','h'],
                   'z':['i','j','k','l','m','n','o','p']})
df
>>>
             x  y   z
0   ab_c_1.0.0  a   i
1   ab_c_1.0.1  b   j
2   ab_c_1.0.2  c   k
3   ab_c_1.1.0  d   l
4   ab_c_1.1.1  e   m
5   ab_c_1.2.0  f   n
6   ab_c_1.3.0  g   o
7   ab_c_1.3.1  h   p

所需输出:

[[('a', 'i'), ('b', 'j'), ('c', 'k')],
 [('d', 'l'), ('e', 'm')],
 [('f', 'n')],
 [('g', 'o'), ('h', 'p')]]

到目前为止,我认为我可以合并这样的东西来获得,可以说,钥匙:

for a in df['x']:
    if a.endswith('.0'):

用这个:

df.values.tolist()

但是,多次迭代多个对象显然是非常低效的。主要的问题是,除了检查x列中字符串的最后一个数字是否为0之外,我不能用任何常量对df进行切片,所以我不能使用滚动窗口或类似的东西。任何建议将不胜感激。

62lalag4

62lalag41#

你可以使用列表解析和groupby

out = [list(zip(g['y'], g['z'])) for k, g in
       df.groupby(df['x'].str.endswith('0').cumsum())]

x的前导部分视为分组器的变体,不包括最后一位数字:

out = [list(zip(g['y'], g['z'])) for k, g in
       df.groupby(df['x'].str.extract(r'(.*).\d', expand=False))]

输出:

[[('a', 'i'), ('b', 'j'), ('c', 'k')],
 [('d', 'l'), ('e', 'm')],
 [('f', 'n')],
 [('g', 'o'), ('h', 'p')]]
8zzbczxx

8zzbczxx2#

我会首先找到x列上的索引,从零开始。

left = 0 
right = 1
slices = []
column_x = df['x']
while right < len(df):
    if column_x[right][-1] == '0':
        slices.append((left, right))
        left = right 
    right += 1
slices.append((left, right))

我的slices数组显示了这些索引

[(0, 3), (3, 5), (5, 6), (6, 8)]

然后我会循环遍历所有切片,然后循环遍历切片的范围。

outer_list = []
for slice in slices:
    inner_list = []
    for index in range(slice[0], slice[1]):
        inner_list.append((df.iloc[index, 1], df.iloc[index, 2]))
    outer_list.append(inner_list)

print(outer_list)
[[('a', 'i'), ('b', 'j'), ('c', 'k')],
 [('d', 'l'), ('e', 'm')],
 [('f', 'n')],
 [('g', 'o'), ('h', 'p')]]

您将在outer_list列表中获得所需的结果

nzrxty8p

nzrxty8p3#

这里有一个方法:

res = ( df
    .assign(x=df.x.str.extract(r'[^.]*\.([^.]*)')).set_index('x')
    .apply(tuple, axis=1).groupby('x').agg(list).tolist() )

输出:

[[('a', 'i'), ('b', 'j'), ('c', 'k')], [('d', 'l'), ('e', 'm')], [('f', 'n')], [('g', 'o'), ('h', 'p')]]

请注意,传递给extract()的模式参数只是一个示例,可以调整它以获取列x中的任何一个组件,该组件是所有行的公共组件,这些行的元组应该在结果中分组在一起。(我使用的模式提取了x列中以点分隔的字符串值中的第二子串。)

相关问题