Разделить строку значения ключа в python и переместить ее в столбец df - PullRequest
1 голос
/ 14 марта 2019

Вот столбец, который у меня есть, я хочу разделить на значение ключа и сохранить в новом столбце в pandas df.

{"FontStyle"=>"Gill Sans Standard", "FontSize"=>"Medium (3mm)"}
{"Font Style"=>"Gill Sans Standard","Font Size"=>"Medium (3mm)"}
{"Font Style":"Script","Font Size":"Medium (3mm)"}
{"Font Style"=>"Gill Sans Standard","Font Size"=>"Medium (3mm)"}
{"Font Style":"Gill Sans Standard","Font Size":"Medium (3mm)"}

Основная проблема в том, что у некоторых из них есть '=>', а у некоторых двоеточие

Мне нужны два новых столбца в df, один для стиля шрифта, другой для размера шрифта и соответствующих значений в них

если бы кто-нибудь мог помочь мне достичь этого, тогда было бы замечательно, а также если бы вы могли порекомендовать мне какую-нибудь книгу / учебник по регулярным выражениям, который был бы великолепен.

Спасибо

Ответы [ 3 ]

1 голос
/ 14 марта 2019

Это далеко не самый эффективный код, но с этим можно справиться.

import pandas as pd
import ast

text = '''{"FontStyle"=>"Gill Sans Standard", "FontSize"=>"Medium (3mm)"}
{"Font Style"=>"Gill Sans Standard","Font Size"=>"Medium (3mm)"}
{"Font Style"=>"Script","Font Size"=>"Medium (3mm)"}
{"Font Style"=>"Gill Sans Standard","Font Size"=>"Medium (3mm)"}'''

my_list = []

text = text.replace("FontStyle", "Font Style")
text = text.replace("FontSize", "Font Size")
text = text.replace("=>", ":")
text = text.split("\n")

for one_dict in text:
    my_list.append(ast.literal_eval(one_dict))

df = pd.DataFrame(my_list)
print(df)

Вывод для приведенного выше кода:

      Font Size          Font Style
0  Medium (3mm)  Gill Sans Standard
1  Medium (3mm)  Gill Sans Standard
2  Medium (3mm)              Script
3  Medium (3mm)  Gill Sans Standard

Надеюсь, это поможет.:-) Дайте мне знать, если это так.

1 голос
/ 14 марта 2019

Попробуйте это:

import ast
df['col'] = df['col'].str.replace('=>', ': ').str.replace('FontSize', 'Font Size').str.replace('FontStyle', 'Font Style')
df['col']= df["col"].apply(lambda x : dict(ast.literal_eval(x)))
df1 = df['col'].apply(pd.Series)
0 голосов
/ 14 марта 2019

Я думаю regex здесь не обязательно, используйте:

import ast

print (df)
                                                 col
0  {"FontStyle"=>"Gill Sans Standard", "FontSize"...
1  {"Font Style"=>"Gill Sans Standard","Font Size...
2  {"Font Style":"Script","Font Size":"Medium (3m...
3  {"Font Style"=>"Gill Sans Standard","Font Size...
4  {"Font Style":"Gill Sans Standard","Font Size"...
5                                                NaN

d = {'=>':':', 'FontSize':'Font Size','FontStyle':'Font Style'}

regex = '|'.join(r"{}".format(x) for x in d.keys())
df1 = (df['col'].dropna()
                .str.replace(regex, lambda x: d[x.group()], regex=True)
                .apply(ast.literal_eval))
df2 = pd.DataFrame(df1.values.tolist())[['Font Size','Font Style']].dropna(how='all')
print (df2)
      Font Size          Font Style
0  Medium (3mm)  Gill Sans Standard
1  Medium (3mm)  Gill Sans Standard
2  Medium (3mm)              Script
3  Medium (3mm)  Gill Sans Standard
4  Medium (3mm)  Gill Sans Standard

Объяснение

  1. Сначала удалите недостающие строки с помощью DataFrame.dropna
  2. Затем используйте Series.str.replace для значений в словаре
  3. Преобразование значений в словари по ast.literal_eval
  4. Создать новый DataFrame
  5. При необходимости фильтровать только столбцы по списку и удалять только NaN s строк
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...