我试图在dask数据框中创建一个新列,其值将是来自另一个数据框的特定索引值。
import pandas as pd
import numpy as np
import dask.dataframe as dd
holdings=pd.DataFrame({'cusip': ['abcd', 'efgh', 'ijkl'], 'date': ['1/1/2000', '1/1/2005', '1/1/2010']})
ratings=pd.DataFrame({'cusip':['abcd','efgh','efgh'],'date':['1/1/2001','1/1/2004','1/1/2006'],'rating':['A','AAA','B']}
dd.from_pandas(df1, npartitions=2)
日期均为datetime.date类型。目的是对于馆藏中的每一行,新列将包含评级中的索引,其中该行包含在馆藏日期中该客户的最新可用评级。例如,馆藏中新列的第二行应包含指向评分第二行的索引。
我编写了以下代码,这些代码可以在保有量和额定值只是熊猫数据帧(而不是dask)时做我要寻找的东西:
def get_rating_index(cusip,date,ratings):
if cusip in ratings['cusip'].values:
temp=ratings[ratings['cusip']==cusip]
avail_ratings=temp[temp['date'].apply(lambda x: x<date)]
if avail_ratings.shape[0]>0:
final=avail_ratings[avail_ratings['date']==max(avail_ratings['date'].values)]
return final.index[0]
else:
return np.nan
else:
return np.nan
holdings['ratings_match']=pd.Series(get_rating_index(holdings['cusip'][i],holdings['date'][i],ratings) for i in holdings.index)
This post对于我需要应用于同一数据的简单函数很有帮助,但是当我尝试将其用于此任务时,出现错误:“数组块大小未知:%s' ,(楠,),“发生在索引0”。
这是我与dask一起使用的确切代码(对我与pandas一起使用的功能进行了一些修改):
def get_rating_index(row):
if row['cusip'] in ratings['cusip'].values:
temp=ratings[ratings['cusip']==row['cusip']]
avail_ratings=temp[temp['date'].apply(lambda x: x<row['date'])]
if avail_ratings.shape[0]>0:
final=avail_ratings[avail_ratings['date']==max(avail_ratings['date'].values)]
return final.index[0]
else:
return -1
else:
return -1
holdings['ratings_match'] = holdings.apply(get_rating_index,meta='int', axis=1)
关于如何在不出现此错误的情况下执行此操作的任何想法?我应该注意,当我尝试查看数据时(例如,使用holdings.head()
),该错误发生一次,而不是在创建列时立即发生。
答案 0 :(得分:0)
这还不是一个完整的答案,但可能会让您入门:
holdings.apply(get_rating_index, meta='int', axis=1)
您实际上很想在这里map
或map_partition
的可能性是 。它们使您可以更直接的方式从Pandas进行概括,并且通常效率更高。
实际上,您正在运行的功能get_rating_index
很像单个映射或在何处进行操作,尽管很难说出意图是什么。另一方面,temp=ratings[ratings['cusip']==row['cusip']]
看起来像一个groupby操作。