重建熊猫数据框

时间:2020-11-05 10:18:24

标签: python pandas dataframe

对Python来说是很新的东西。 我在重建不良的Dataframe时遇到麻烦。我的数据框如下所示:

df = pd.DataFrame({'col1': ['id 1', 'id 2', 'test 3', 'test 4'],
               'col2': ['test 1', 'test 2',
                        'Number 6135', 'id 4'],
               'col3': ['Number 12344', 'Number 21612','id 3','Number 1131']})

enter image description here

您可以看到,我在第一,第二和Thrid栏位中都有“ id”。其他值也一样。

我的目标是在每个Col中都有一个数据框,其中只有以Same子字符串开头的值,例如以下示例:

enter image description here

我已经尝试过使用for循环和Statments来检查我的String中是否有某个子字符串。如果是的话,我会创建一个新列并在其中写入我的值

for x in df['col1']:
if 'id' in x:
    df['newCol']=x

我知道这段代码永远无法解决我的问题,也许有些熊猫函数可以帮助我解决这个问题

如果不清楚,请问我,我会尽力解释我的问题。 预先感谢您的帮助,并轻松一点:)

4 个答案:

答案 0 :(得分:3)

您可以将sorted()与自定义键功能一起使用:

def key_fn(x):
    if 'id' in x:
        return 0
    if 'test' in x:
        return 1
    if 'Number' in x:
        return 2
    return 3 

df = df.apply(lambda x: pd.Series(sorted(x, key=key_fn)), axis=1)
df = df.rename(columns=lambda x: 'col{}'.format(x+1))
print(df)

打印:

   col1    col2          col3
0  id 1  test 1  Number 12344
1  id 2  test 2  Number 21612
2  id 3  test 3   Number 6135
3  id 4  test 4   Number 1131

另一个版本,摘自评论:

df = pd.DataFrame([sorted(l, key=key_fn) for l in df.values], columns=df.columns)
print(df)

答案 1 :(得分:3)

如果可能的话,可以通过用第一个空格分隔值来简化解决方案:

df = (df.reset_index()
        .melt('index')
        .assign(new = lambda x: x['value'].str.split().str[0])
        .pivot('index','new','value'))
print (df)
new          Number    id    test
index                            
0      Number 12344  id 1  test 1
1      Number 21612  id 2  test 2
2       Number 6135  id 3  test 3
3       Number 1131  id 4  test 4

否则,您可以使用Series.str.extract

L = ['id','test','Number']

df = (df.reset_index()
        .melt('index')
        .assign(new = lambda x: x['value'].str.extract(f'({"|".join(L)})', expand=False))
        .pivot('index','new','value'))
print (df)
new          Number    id    test
index                            
0      Number 12344  id 1  test 1
1      Number 21612  id 2  test 2
2       Number 6135  id 3  test 3
3       Number 1131  id 4  test 4

答案 2 :(得分:0)

尝试一下:

s = df.melt()['value']
df_final = pd.DataFrame({x: s[s.str.startswith(x)].values 
                                        for x in s.str.split().str[0].unique()})

Out[27]:
     id    test        Number
0  id 1  test 3   Number 6135
1  id 2  test 4  Number 12344
2  id 4  test 1  Number 21612
3  id 3  test 2   Number 1131

答案 3 :(得分:0)

您可以首先melt数据框,然后使用numpy select重新命名名称,最后使用pivot

(df.melt(ignore_index=False)
   .assign(variable=lambda x: np.select([x.value.str.startswith("id"),
                                          x.value.str.startswith("test"),
                                          x.value.str.startswith("Number")],
                                          ["col1", "col2", "col3"]))
    .reset_index()
    .pivot("index", "variable", "value")
    .rename_axis(columns=None, index=None))


    col1    col2    col3
0   id 1    test 1  Number 12344
1   id 2    test 2  Number 21612
2   id 3    test 3  Number 6135
3   id 4    test 4  Number 1131