-1

Python/pandas 新手在这里。我正在尝试使用的 csv 文件已填充了如下所示的数据:

A                                                      B            C       D
Option1(item1=12345, item12='string', item345=0.123)   2020-03-16   1.234   Option2(item4=123, item56=234, item678=345)

我希望它看起来像这样:

item1   item12     item345   B            C      item4   item56   item678
12345   'string'   0.123     2020-03-16   1.234  123     234      345

换句话说,我想用等号左侧的新列替换列 A 和 D,使用等号右侧的内容作为对应值,并使用 Option1() 和 Option2()部分和逗号被删除。不包含函数的列应保持原样。

有没有一种优雅的方式来做到这一点?

实际上,在这一点上,我会满足于任何旧方式,无论是否优雅;如果有字典填充列,我已经找到了处理这种情况的各种方法,但是如果那里有函数,没有什么可以帮助我把它分开。试图寻找答案只会给我一堆关于如何函数应用于数据框的结果。

4

2 回答 2

1

只要您的函数始终具有相同的参数,这应该可以工作。

您可以阅读 csv(如果分隔符是 2 个或更多空格,这就是我粘贴您的问题示例时得到的结果):

df = pd.read_csv('test.csv',sep='[\s]{2,}', index_col=False, engine='python')

如果您的数据框是df

# break out both sides of the equal sign in function into columns
A_vals = df['A'].str.extractall(r'([\w\d]+)=([^,\)]*)')

# get rid of the multi-index and put the values after '=' into columns
A_converted = A_vals.unstack(level=-1)[1]

# set column names to values before '='
A_converted.columns = list(A_vals.unstack(level=-1)[0].values[0])

# same thing for 'D'
D_vals = df['D'].str.extractall(r'([\w\d]+)=([^,\)]*)')
D_converted = D_vals.unstack(level=-1)[1]
D_converted.columns = list(D_vals.unstack(level=-1)[0].values[0])

# join everything together
df = A_converted.join(df.drop(['A','D'], axis=1)).join(D_converted)

关于正则表达式的一些说明'([\w\d]+)=([^,\)]*)'有两个捕获组(每个部分都在括号中):

第 1 组([\w\d]+)是一个或多个字符 ( +),它们是单词字符\w或数字\d

=组之间。

第 2 组([^,\)]*)是 0 个或多个字符 ( *),而不是 ( ^) 逗号,或括号\)

于 2020-03-17T01:27:44.303 回答
0

我相信您正在寻找以下方面的东西:

contracts = ["Option(conId=384688665, symbol='SPX', lastTradeDateOrContractMonth='20200116', strike=3205.0, right='P', multiplier='100', exchange='SMART', currency='USD', localSymbol='SPX   200117P03205000', tradingClass='SPX')",    
"Option(conId=12345678, symbol='DJX', lastTradeDateOrContractMonth='20200113', strike=1205.0, right='P', multiplier='200', exchange='SMART', currency='USD', localSymbol='DJXX   333117Y13205000', tradingClass='DJX')"]

new_conts = []
columns = []

for i in range (len(contracts)):
    mod = contracts[i].replace('Option(','').replace(')','')
    contracts[i] = mod    
    new_cont = contracts[i].split(',')
    new_conts.append(new_cont)

for contract in new_conts:
    column = []
    for i in range (len(contract)):
        mod = contract[i].split('=')
        contract[i] = mod[1]
        column.append(mod[0])
    columns.append(column)

print(len(columns[0]))
df = pd.DataFrame(new_conts,columns=columns[0])
df

输出:

    conId   symbol  lastTradeDateOrContractMonth    strike  right   multiplier  exchange    currency    localSymbol     tradingClass
0   384688665   'SPX'   '20200116'  3205.0  'P'     '100'   'SMART'     'USD'   'SPX 200117P03205000'   'SPX'
1   12345678    'DJX'   '20200113'  1205.0  'P'     '200'   'SMART'     'USD'   'DJXX 333117Y13205000'  'DJX'

显然,您可以删除不需要的列、更改名称等。

于 2020-03-17T17:58:31.763 回答