2015-10-19 91 views
0

假设我有一个形状=(2,500,000,M)的熊猫数据框和形状(2,500,000,N)的scipy csr稀疏矩阵。基于熊猫数据帧的索引从稀疏矩阵中选择行

数据帧和稀疏矩阵的每一行描述了一个实体。它们已经被排序,使得数据帧的第1行正在描述也在稀疏矩阵的第1行中找到的实体。所以现在数据帧有一个快速机制来做滤波(catalogue.where(catalogue.some_column != ''),但是如何在给定滤波数据帧的稀疏矩阵中找到相应的行?

假设数据帧被称为catalogue,和稀疏矩阵称为collection

def collection_filter_row(catalogue_filtered, catalogue_index_full, collection): 
    return scipy.sparse.vstack(ThreadPool(100).map(
     functools.partial(collection_get_row, 
      catalogue_index=tuple(catalogue_index_full), 
      collection=collection), 
     tuple(catalogue_filtered.index.values))) 

def collection_get_row(document_id, catalogue_index, collection): 
    return collection.getrow(catalogue_index.index(document_id)) 

collection_partial = partial(
    collection_filter_row, 
    catalogue_index_full=catalogue.index.values, 
    collection=pickle.load(open('collection-tfidf', 'rb'))) 
criteria = catalogue['criteria'].where(catalogue.criteria != '') 
collection_state = collection_partial(criteria) 

但即使有任何种类的多处理的(GEVENT,线程池),它仍然是缓慢的回暖各行,我是否做错了什么(或者说,是否有更快的方式来做这件事)?

+0

'vstack'是'稀疏'版本? – hpaulj

+0

您是否了解哪些步骤需要时间?没有游泳池,“collection.getrow”是一个缓慢的步骤?或'catalogue_index.index'?多处理的东西可能正在工作,但它掩盖了稀疏索引步骤 - 这似乎是你问的部分。 – hpaulj

+0

您是否探索过一次从'collection'中选择多行?它如何扩展? – hpaulj

回答

0

以某种方式找到了解决此问题的更快方法。首先创建一个catalogue index =>collection索引字典。

index_dict = dict(zip(
    catalogue.index.values.tolist(), 
    range(collection.shape[0]))) 

然后我collection_filter_row成为

def collection_filter_row(catalogue_filtered, index_dict, collection): 
    return collection[[index_dict[document_id] 
         for document_id 
         in catalogue_filtered.index.values.tolist()]] 

为了回报而不是使用catalogue.where()我真的应该使用catalogue.loc[catalogue.some_column != '']集合的子集,所以collection_filter_row适当的呼叫,然后

collection_sub = collection_filter_row(
    catalogue.loc[catalogue.some_column != ''], 
    index_dict, 
    collection) 

比问题中显示的原始方法快得多