python - 对公司名称的 DataFrame 进行非规范化 [第 2 部分]

标签 python pandas dataframe

这是我的 previous post 的延续关于对公司名称的 DataFrame 进行非规范化。

我现在正在使用的修改后的表格如下:

import numpy as np
import pandas as pd

df = pd.DataFrame({'name' : ['Nitron', 'Pulset', 'Rotaxi'], 
                   'postal_code' : [1410, 1020, 1310], 
                   'previous_name1' : ['Rotory', np.NaN, 'Datec'],
                   'previous_name2' : [ np.NaN, 'Cmotor', np.NaN],
                   'previous_name3' : ['Datec', np.NaN, np.NaN],
                   'country' : ['BEL', 'ENG', 'JPN'], 
                   'city' : ['Brussels', np.NaN, np.NaN]
                  })

print(df)

| name   | postal_code | previous_name1 | previous_name2 | previous_name3 | country | city     |
|--------|-------------|----------------|----------------|----------------|---------|----------|
| Nitron | 1410        | Rotory         | NaN            | Datec          | BEL     | Brussels |
| Pulset | 1020        | NaN            | Cmotor         | NaN            | ENG     | NaN      |
| Rotaxi | 1310        | Cyclip         | NaN            | NaN            | JPN     | NaN      |

与我之前的文章相比,上面的 DataFrame 现在多了两列,即 countrycity系列。

我的目标保持不变:为先前公司名称不缺失的所有实例添加一个新行使用 countrycity columns 并删除以前的名称系列。从视觉上看,“非规范化”版本应如下所示:

| name   | postal_code | country | city     |
|--------|-------------|---------|----------|
| Nitron | 1410        | BEL     | Brussels |
| Rotory | 1410        | BEL     | Brussels |
| Datec  | 1410        | BEL     | Brussels |
| Pulset | 1020        | ENG     | NaN      |
| Cmotor | 1020        | ENG     | NaN      |
| Rotaxi | 1310        | JPN     | NaN      |
| Cyclip | 1310        | JPN     | NaN      |

花了一些时间了解 the code 后对于我之前的问题,由 jezrael 提供,我尝试修改/调整这个新问题的解决方案,但没有成功。由于我对 Python/Pandas 生态系统相当陌生,因此我们将不胜感激任何额外的帮助。

最佳答案

您可以在set_index中添加多个列,并将level=1更改为level=3以删除MultiIndex<的第四级:

df1 = (df.set_index(['postal_code','country','city'])
         .stack()
         .reset_index(level=3, drop=True)
         .reset_index(name='name')
         )
print (df1)
   postal_code country      city    name
0         1410     BEL  Brussels  Nitron
1         1410     BEL  Brussels  Rotory
2         1410     BEL  Brussels   Datec
3         1020     ENG       NaN  Pulset
4         1020     ENG       NaN  Cmotor
5         1310     JPN       NaN  Rotaxi
6         1310     JPN       NaN   Datec

对于第二种解决方案,将多列添加到melt:

df1 = (df.melt(['postal_code','country','city'], value_name='name')
         .drop('variable', axis=1)
         .dropna(subset=['name'])
         .reset_index( drop=True)
)
print (df1)
   postal_code country      city    name
0         1410     BEL  Brussels  Nitron
1         1020     ENG       NaN  Pulset
2         1310     JPN       NaN  Rotaxi
3         1410     BEL  Brussels  Rotory
4         1310     JPN       NaN   Datec
5         1020     ENG       NaN  Cmotor
6         1410     BEL  Brussels   Datec

关于python - 对公司名称的 DataFrame 进行非规范化 [第 2 部分],我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56924682/

相关文章:

python - 从字符串中删除多个单词的更好方法?

python - 用前面提到的人替换人称代词(嘈杂的 coref)

python - 无法导入 Pandas_Datareader

python - 如何从 pandas Dataframe 创建单个字典?

python - 如何按列提取pd行,并向左移动2列

python - 尝试使用 Python 获取 Excel 差异时如何修复 Key 错误

python - Pandas 在 Python 的应用函数中按列名获取行值?

Python、Pandas 删除 Excel 中的行

python - 将 RandomForestClassifier Predict_Proba 结果添加到原始 Dataframe

python - pandas argsort 如何将 nan 保留为 nan?