首页 > 解决方案 > Python:根据条件拆分单列

问题描述

我有一个应该是 json 的 csv,我正在尝试在多个列中对其进行排序

它可能是这样的json(如果有帮助的话):

{"username":"jane.doe@gmail.com"
   "app": [
        {"appid":"123456"
        "appname:"apppname"
        "scopes":["scope1","scope2"]}
        {"appid":"23456
        "appname:"apppname"2
        "scopes":["scope1","scope2"]}
{"username":john.doe@gmail.com"
   ...}

这是数据

价值
用户:jane.doe@gmail.com
客户编号:CI1
匿名:假
显示文本:app1
本机应用程序:错误
用户密钥:uk1
范围:
http://scope1.com
http://scope2.com
客户编号:CI2
匿名:假
显示文本:app2
本机应用程序:错误
用户密钥:uk2
范围:
http://scopeapp2-1.com
http://scopeapp2-1.com

它继续下去,用户可以拥有任意数量的应用程序,并且应用程序可以有很多范围。预期产出

用户 匿名的 显示文本 原生应用 范围 Client_id 用户密钥
jane.doe@gmail.com 错误的 应用程序1 错误的 http://scope1.com http://scope2.com CI1 英国1
jane.doe@gmail.com 错误的 应用程序2 错误的 https://scopeapp2-1.com http://scopeapp2-2.com CI2 英国2

所以我做到了,但我认为我的代码有点难看,想知道你是否有更好的想法

for index, row in df.iterrows():
    if 'User' in df.at[index,'value']:
        x=index
        df.at[x,'User']=df.at[index,'value']
    elif 'Client ID' in df.at[index,'value']:
        df.at[x,'Client_ID']=df.at[index,'value']
        x=x+1
    elif 'anonymous' in df.at[index,'value']:
        df.at[x,'anonymous']=df.at[index,'value']       
    elif 'displayText' in df.at[index,'value']:
        df.at[x,'displayText']=df.at[index,'value']   
    elif 'nativeApp' in df.at[index,'value']:
        df.at[x,'nativeApp']=df.at[index,'value']   
    elif 'userKey' in df.at[index,'value']:
        df.at[x,'userKey']=df.at[index,'value']
    elif 'http' in df.at[index,'value']:
        df.at[x,'scopes']=df.at[x,'scopes'] + ' ' +df.at[index,'value']

然后我将删除空行。我想知道是否有更好的方法来做到这一点,所有这些 elif 都不是很干净......

任何帮助,将不胜感激。

标签: pythonpandasjupyterdata-cleaning

解决方案


我假设你的意思是你有一个 csv 文件。

如果您可以依靠结构,即 1 个用户,1 到 N 个客户端 ID 部分,其范围部分带有 1 .. N 个 url,您可以执行以下操作:

if __name__ == '__main__':
    from itertools import islice
    from pprint import pprint
    data = {}


    def fieldv(line):
        return line.rsplit(':', 1)[1].strip()


    users = []
    client_data = []
    user_record = None
    scopes = []
    with open(..., 'r') as infile:
        while line := infile.readline():
            if line.startswith('User'):
                user = fieldv(line)
                client_data = []
                user_record = {'User': user, 'client_data': client_data}
                users.append(user_record)
            elif line.startswith('http://'):
                scopes.append(line.strip())
            else:
                d = list(islice(infile, 5))
                scopes = []
                app = {'Client ID': fieldv(line),
                       'anonymous': fieldv(d[0]),
                       # other fields d[1], d[2]...,
                       'scopes': scopes}
                client_data.append(app)

使用提供的数据打印用户列表:

[{'User': 'jane.doe@gmail.com',
  'client_data': [{'Client ID': 'CI1',
                   'anonymous': 'False',
                   'scopes': ['http://scope1.com', 'http://scope2.com']},
                  {'Client ID': 'CI2',
                   'anonymous': 'False',
                   'scopes': ['http://scopeapp2-1.com',
                              'http://scopeapp2-1.com']}]}]

推荐阅读