我从excel输入中制作测试团队报告;使用pandas来收集,过滤,处理数据。
我在下面的代码中制作了产品测试用封面表供以后使用/轻松搜索。第3列是测试用例的类型。我在一个excel中有多个测试用例,所以我需要通过所有单元格和拆分测试来制作成对产品 - 测试用例。
因为我对大熊猫并不熟悉,而且我在其他地方找不到更好的方法,我想问一下是否有更多的pythonic方式或者更容易用pandas方式来做同样和更有效的方法。 / p>
带有示例数据的代码(\ n是excel单元格中的换行符):
df = pd.DataFrame({"prod":["TS001","TS002"],
"activate":["001_002\n001_004", "003_008\n024_080"],
"deactivate":["004_005\n006_008", "001_008"]})
df = df.set_index("prod")
list_of_tuples = []
for i, row in df.iterrows():
for cell in row.iteritems():
for test in cell[-1].splitlines():
list_of_tuples.append((i, test, cell[0])) # [(product, test, category)..]
return_df = pd.DataFrame(list_of_tuples, columns=('prod', 'testcase', 'category'))
制造
prod testcase category
0 TS001 001_002 activate
1 TS001 001_004 activate
2 TS001 004_005 deactivate
3 TS001 006_008 deactivate
4 TS002 003_008 activate
5 TS002 024_080 activate
6 TS002 001_008 deactivate
感谢您提出任何建议。
答案 0 :(得分:4)
理解
pd.DataFrame(
[(p, t, c) for (p, c), r in df.stack().items() for t in r.split()],
columns=['prod', 'testcase', 'category']
)
prod testcase category
0 TS001 001_002 activate
1 TS001 001_004 activate
2 TS001 004_005 deactivate
3 TS001 006_008 deactivate
4 TS002 003_008 activate
5 TS002 024_080 activate
6 TS002 001_008 deactivate
解释
df.stack()
prod
TS001 activate 001_002\n001_004
deactivate 004_005\n006_008
TS002 activate 003_008\n024_080
deactivate 001_008
dtype: object
当迭代df.stack().items()
时,我们得到索引值为第一个元素的元组,值为第二个元素。因为我们堆叠,索引值本身就是一个元组。所以第一对看起来像:
(('TS001', 'activate'), '001_002\n001_004')
通过对'001_002\n001_004'.split()
的后续迭代并重新排列解压缩的元素,我们得到
[(p, t, c) for (p, c), r in df.stack().items() for t in r.split()]
[('TS001', '001_002', 'activate'),
('TS001', '001_004', 'activate'),
('TS001', '004_005', 'deactivate'),
('TS001', '006_008', 'deactivate'),
('TS002', '003_008', 'activate'),
('TS002', '024_080', 'activate'),
('TS002', '001_008', 'deactivate')]
然后我将它包装在pd.DataFrame
构造函数中,我在其中命名列。
答案 1 :(得分:2)
使用:
set_index
喜欢你的解决方案apply
,用split
和DataFrame
处理expand=True
的lambda函数的多列,并按stack
重新整形Multiindex
的列,unstack
reset_index
首先删除级别,然后Multiindex
添加到列reindex_axis
了解列的更改顺序df = (df.set_index('prod')
.apply(lambda x: x.str.split('\n', expand=True).unstack())
.stack()
.reset_index(level=0, drop=True)
.reset_index(name='testcase')
.rename(columns={'level_1':'category'})
.reindex_axis(['prod','testcase','category'], axis=1))
print (df)
prod testcase category
0 TS001 001_002 activate
1 TS001 004_005 deactivate
2 TS002 003_008 activate
3 TS002 001_008 deactivate
4 TS001 001_004 activate
5 TS001 006_008 deactivate
6 TS002 024_080 activate
答案 2 :(得分:1)
这是一种方式,可以有更好的方法。检查piRSquared - 在这里应该是效率最高的。
In [2807]: (df.set_index('prod')
.applymap(lambda x: x.split('\n'))
.stack()
.apply(pd.Series)
.stack()
.reset_index(name='testcase')
.rename(columns={'level_1': 'category'})
.drop('level_2', 1))
Out[2807]:
prod category testcase
0 TS001 activate 001_002
1 TS001 activate 001_004
2 TS001 deactivate 004_005
3 TS001 deactivate 006_008
4 TS002 activate 003_008
5 TS002 activate 024_080
6 TS002 deactivate 001_008
详细
In [2809]: df
Out[2809]:
activate deactivate prod
0 001_002\n001_004 004_005\n006_008 TS001
1 003_008\n024_080 001_008 TS002
答案 3 :(得分:1)
使用 df.applymap
, df.melt
和 df.stack
df = df.applymap(str.split).reset_index().melt('prod', \
['activate', 'deactivate']).set_index(['prod', 'variable'])
df = pd.DataFrame(df.value.tolist(), index=df.index)\
.stack().reset_index().drop('level_2', 1)
df.columns = ['prod', 'category', 'testcase']
df
prod category testcase
0 TS001 activate 001_002
1 TS001 activate 001_004
2 TS002 activate 003_008
3 TS002 activate 024_080
4 TS001 deactivate 004_005
5 TS001 deactivate 006_008
6 TS002 deactivate 001_008