python-3.x - Python:从数据框字符串列中提取维度数据并为每个列创建具有值的列
问题描述
嘿嘿,
我有一个包含 2 列的源文件:ID 和 all_dimensions。所有维度都是具有不同“键值”对的字符串,每个 id 都不相同。我想制作键列标题并解析相应的值(如果存在于正确的单元格中)。
例子:
ID all_dimensions
12 Height:2 cm,Volume: 4cl,Weight:100g
34 Length: 10cm, Height: 5 cm
56 Depth: 80cm
78 Weight: 2 kg, Length: 7 cm
90 Diameter: 4 cm, Volume: 50 cl
期望的结果:
ID Height Volume Weight Length Depth Diameter
12 2 cm 4cl 100g - - -
34 5 cm - - 10cm - -
56 - - - - 80cm -
78 - - 2 kg 7 cm - -
90 - 50 cl - - - 4 cm
我确实有超过 100 个维度,所以理想情况下我想编写一个 for 循环或类似的东西来不指定每个列标题(请参阅下面的代码示例)我使用的是 Python 3.7.3 和 pandas 0.24.2。
我已经尝试了什么:
1)我试图将数据拆分为单独的列,但不确定如何继续将每个值分配到正确的标题中:
df.set_index('ID',inplace=True)
newdf = df["all_dimensions"].str.split(",|:",expand = True)
2)使用初始df,我使用“str.extract”来创建新列(但是我需要指定每个标题):
df['Volume']=df.all_dimensions.str.extract(r'Volume:([\w\s.]*)').fillna('')
3) 为了解决 2) 每个标题的问题,我创建了所有维度属性的列表,并考虑使用带有 for 循环的列表来提取值:
columns_list=df.all_dimensions.str.extract(r'^([\D]*):',expand=True).drop_duplicates()
columns_list=columns_list[0].str.strip().values.tolist()
for dimension in columns_list:
df.dimension=df.all_dimensions.str.extract(r'dimension([\w\s.]*)').fillna('')
在这里,JupyterNB 给了我一个 UserWarning:“Pandas 不允许通过新属性名称创建列”并且 df 看起来和以前一样。
解决方案
选项1:我更喜欢拆分几次:
new_series = (df.set_index('ID')
.all_dimensions
.str.split(',', expand=True)
.stack()
.reset_index(level=-1, drop=True)
)
# split second time for individual measurement
new_df = (new_series.str
.split(':', expand=True)
.reset_index()
)
# stripping off leading/trailing spaces
new_df[0] = new_df[0].str.strip()
new_df[1] = new_df[1].str.strip()
# unstack to get the desire table:
new_df.set_index(['ID', 0])[1].unstack()
选项 2:split(',|:')
按照您尝试的方式使用:
# splitting
new_series = (df.set_index('ID')
.all_dimensions
.str.split(',|:', expand=True)
.stack()
.reset_index(level=-1, drop=True)
)
# concat along axis=1 to get dataframe with two columns
# new_df.columns = ('ID', 0, 1) where 0 is measurement name
new_df = (pd.concat((new_series[::2].str.strip(),
new_series[1::2]), axis=1)
.reset_index())
new_df.set_index(['ID', 0])[1].unstack()
输出:
Depth Diameter Height Length Volume Weight
ID
12 NaN NaN 2 cm NaN 4cl 100g
34 NaN NaN 5 cm 10cm NaN NaN
56 80cm NaN NaN NaN NaN NaN
78 NaN NaN NaN 7 cm NaN 2 kg
90 NaN 4 cm NaN NaN 50 cl NaN
推荐阅读
- r - 将报表函数的输出从报表包渲染到 knitr
- python - Python从源递归解压缩到另一个目的地
- mysql - 无法对父子层次结构进行排序
- azure - 向事件中心发送有关成功插入数据库的事件时如何确保可靠发布?
- node.js - 出口交易需要客户的姓名和地址
- c++ - C++ - 覆盖虚拟模板化成员函数
- compiler-construction - 警告:转移/减少冲突
- android - 臭名昭著的高度:Android 版 chrome 上的 100% 问题 - 地址栏
- python - Django Celery 背景刮板
- python - 如何在数据框中查找值并使用 python/pandas 返回匹配值?