Python 使用分隔符从列表中提取数据

Python 使用分隔符从列表中提取数据,python,string,pandas,list,Python,String,Pandas,List,我有一组10个python列表,格式如下: [ABC*DEF*123>~123*999*HHH] [PQR*RST*567>~AWS*999*POI] [XYZ*TGT*234>~2352*245*HFT] [STU*DEF*789>~654*345*QQQ] 我试图从上面的列表中提取数据,以便最终输出是一个数据帧,除了下面的输出之外: 123,999,HHH AWS,999,POI 2352,245,HFT 654,345,QQQ 以下是我迄今为止所做的工作: al

我有一组10个python列表,格式如下:

[ABC*DEF*123>~123*999*HHH]
[PQR*RST*567>~AWS*999*POI]
[XYZ*TGT*234>~2352*245*HFT]
[STU*DEF*789>~654*345*QQQ]
我试图从上面的列表中提取数据,以便最终输出是一个数据帧,除了下面的输出之外

123,999,HHH
AWS,999,POI
2352,245,HFT
654,345,QQQ
以下是我迄今为止所做的工作:

allFiles = Path where all the txt files are stored
list_ = []
for file_ in allFiles:
    with open(file_) as fp:
        lines1 = fp.read().split('\n')
        b = [i.split('~', 1)[1] for i in lines1]
        print(b)
以上为我提供了如下列表:

[123*999*HHH]
[AWS*999*POI]
[2352*245*HFT]
[654*345*QQQ]

我无法使用分隔符(*)提取上述数据并将其拆分为不同的列,并将其保存到数据框中

您可以先创建一个数据框,将字符串列表作为行,然后使用将每个字符串拆分为
~
。然后,您可以仅选择第二个术语,然后再选择另一个拆分,这次是通过
*
,设置
expand=True

l1 = ['ABC*DEF*123>~123*999*HHH']
l2 = ['PQR*RST*567>~AWS*999*POI']
l3 = ['XYZ*TGT*234>~2352*245*HFT']
l4 = ['STU*DEF*789>~654*345*QQQ']

df = pd.DataFrame([l1,l2,l3,l4], columns=['col1'])
df.col1.str.split('~').str[1].str.split('*', expand=True)

     0    1    2
0   123  999  HHH
1   AWS  999  POI
2  2352  245  HFT
3   654  345  QQQ

更新

要使用多个文件中的列表执行上述操作:

l = []
for file_ in allFiles:
    f = open(file_, 'r')
    l.extend([line.rstrip('\n') for line in f.readlines()])
然后像以前一样做:

df = pd.DataFrame(l, columns=['col1'])
df.col1.str.split('~').str[1].str.split('*', expand=True)

因为您已经有了列表,所以一个简单的函数可以在分隔符(*)上拆分

与列表数量无关的更通用的解决方案。这将在形成数据帧之前执行所有拆分操作

#allFiles = Path where all the txt files are stored

def split_delim(Files):  
    list_ = []
    for file_ in Files:
        with open(file_) as fp:
            lines1 = fp.read().split('\n')
            b = [i.split('~', 1)[1] for i in lines1]
            for i in b:
                l = i.split('*')
                list_.append(l)                
    return list_

list_new = split_delim(allFiles)

df = pd.DataFrame(list_new, columns=['col1'])
与分隔符
~
和参数
name
s一起使用,然后为
数据帧的第二列添加:

import pandas as pd

temp=u"""ABC*DEF*123>~123*999*HHH
PQR*RST*567>~AWS*999*POI
XYZ*TGT*234>~2352*245*HFT
STU*DEF*789>~654*345*QQQ"""
#after testing replace 'pd.compat.StringIO(temp)' to 'filename.csv'
df = pd.read_csv(pd.compat.StringIO(temp), sep="~", names=['a','b'])

df = df['b'].str.split('*', expand=True)
print (df)
      0    1    2
0   123  999  HHH
1   AWS  999  POI
2  2352  245  HFT
3   654  345  QQQ
如果要使用您的解决方案,请添加另一个
拆分

list_ = []
for file_ in allFiles:
with open(file_) as fp:
    lines1 = fp.read().split('\n')
    b = [i.split('~', 1)[1].split('*') for i in lines1]
    list_.append(b)

df = pd.DataFrame([y for x in list_ for y in x])
print(df)

例如,必须显式指定分隔符

print('ABC*DEF*123>~123*999*HHH'.split('~')[1].split('*'))
产生:

['123', '999', 'HHH']

谢谢你的回复,但是列表的数量不是固定的。它是动态变化的。我怎样才能完成上述工作,使我们不必定义列表的数量。。谢谢。@scottmartin您的列表是如何保存的?在更大的列表中?我读取的每个文件都存储为一个列表。如我的第一篇文章所示,我从一个文件夹中读取了文件(其中n是文件夹中的文件数),因此有“n”个列表。希望我已经回答了你的问题。谢谢。我添加了另一行,在该行中,我将列表保存到了数据框中,并且只看到保存的最后一个列表/文件
df=pd.DataFrame(b)
请您协助。谢谢。@scottmartin-你现在能查一下吗?再帮个忙。在执行上述拆分后,我有几行的值为0001~ABC。请您告知我如何修改上述代码,以便将此附加拆分(“~”)方法应用于您在上面共享的最新更新代码。@scottmartin-更好的方法是创建新问题。
['123', '999', 'HHH']