2016-01-21 47 views
0

我有一个脚本从数据库中收集数据,过滤并放入列表中以便进一步处理。我已经在几个进程之间拆分了数据库中的条目,以便更快地进行过滤。这里的片段:多重处理卡在加入Windows中

def get_entry(pN,q,entries_indicies): 

    ##collecting and filtering data 
    q.put((address,page_text,)) 
    print("Process %d finished!" % pN) 

def main(): 

    #getting entries 
    data = [] 

    procs = [] 
    for i in range(MAX_PROCESSES): 
     q = Queue() 
     p = Process(target=get_entry,args=(i,q,entries_indicies[i::MAX_PROCESSES],)) 
     procs += [(p,q,)] 
     p.start()  
    for i in procs: 
     i[0].join() 
     while not i[1].empty(): 
      #process returns a tuple (address,full data,) 
      data += [i[1].get()] 
    print("Finished processing database!") 

    #More tasks 
    #................ 

我已经在Linux(Ubuntu 14.04)上运行它,它完全正常。当我在Windows 7上运行它时,问题就开始了。该脚本在16个月中的第11个过程中陷入了i[0].join()(这对我来说完全是随机的)。没有错误信息,没有什么,只是冻结在那里。与此同时,该print("Process %d finished!" % pN)则显示所有进程,这意味着他们都走到了尽头,所以应该有与get_entry

我想评论的过程中功能q.put行的代码没有问题,这一切都过得很好(当然,data结束了空)。

这是否说明Queue这是责任?为什么它会卡住join()?是否因Queue内部的Lock?如果是这样,并且Queue呈现我的脚本在Windows上不可用,是否有其他方法可以将进程收集的数据传递给主进程中的data列表?

回答

0

想出了我最后一个问题的答案。

我用Manager代替

def get_entry(pN,q,entries_indicies): 
    #processing 

    # assignment to manager list in another process doesn't work, but appending does. 
    q += result 

def main(): 

    #blahbalh 

    #getting entries 
    data = [] 

    procs = [] 
    for i in range(MAX_PROCESSES): 
     manager = Manager() 
     q = manager.list() 
     p = Process(target=get_entry,args=(i,q,entries_indicies[i::MAX_PROCESSES],)) 
     procs += [(p,q,)] 
     p.start() 
    # input("Press enter when all processes finish") 
    for i in procs: 
     i[0].join() 
     data += i[1] 
    print("data", data)#debug 
    print("Finished processing database!") 

    #more stuff 

join()在Windows冻结由于Queue存在的本质仍然是个谜。所以问题仍然存在。