簡體   English   中英

聚合列表 dataframe 在 pandas 使用專用 function

[英]Aggregate list dataframe in pandas using dedicated function

我在 pandas 中有以下 dataframe:

data = {'ID_1': {0: '10A00', 1: '10B00', 2: '20001', 3: '20001'},
        'ID_2_LIST': {0: [20009, 30006], 1: [20001, 30006],
                      2: [30009, 30006], 3: [20001, 30003]},
        'ID_OCCURRENCY_LIST': {0: [1, 2], 1: [5, 6], 2: [2, 4], 3: [1, 3]}}

# create df
df = pd.DataFrame(data)

|    | ID_1   | ID_2_LIST      | ID_OCCURRENCY_LIST   |
|---:|:-------|:---------------|:---------------------|
|  0 | 10A00  | [20009, 30006] | [1, 2]               |
|  1 | 10B00  | [20001, 30006] | [5, 6]               |
|  2 | 20001  | [30009, 30006] | [2, 4]               |
|  3 | 20001  | [20001, 30003] | [1, 3]               |

我將通過應用外部 function 的ID_1字段進行聚合(為了識別類似的 ID_1,假設“similarID(ID1,ID2)”,它根據一些內部規則返回 ID1 或 ID2),重新生成 ID2 和 sum 的列表所有相同 ID2 的出現次數。

結果應該是:

  **INDEX    ID_1      ID_2_LIST              ID_OCCURRENCY_LIST**
   0      10A00      [20009,30006,20001]            [1, 8, 5]
   1      10B00      [20001,30006, 30003,20001]     [5, 6, 4, 2]
   1      20001      [30009,30006, 20001,30003]     [2, 4, 1, 3]

編輯function 的代碼如下(s1=第一個字符串,c1=第二個字符串,p1=相似度百分比 l1=置信度,demeraulevenshtein 是文獻函數):

def pySimilar(s1,c1,p1,l1): 
  if s1 is None or c1 is None:
    return 0
  if len(s1)<=5 or len(c1)<=5:
    return 0

  s1=s1.strip()
  c1=c1.strip()
  s=s1
  c=c1
  if s1[3:len(s1)]==c1[3:len(c1)]:
      return 1

  if len(s1)>=len(c1):
    ITERATIONLENGTH=len(c1)/2
  else:
    ITERATIONLENGTH=len(s1)/2

  if len(s1)>=len(c1):
      a=int(len(c1)/2)+1
      if s1.find(c1[3:a])<0:
        return 0  
  else:
      b=int(len(s1)/2)+1
      if c1.find(s1[3:b])<0:
        return 0

  v=[]

  CNT=0
  TMP=0
  max_res=0
  search=s1
  while CNT < ITERATIONLENGTH:
    TMP=(100-((pyDamerauLevenschtein(s[3:len(s)],c[3:len(c)]))*100)/(len(c)-3)) * ((len(search)-3)/(len(s1)-3))
    v.append(TMP)
    CNT=CNT+1
    if TMP>max_res:
        max_res = TMP
    #s=s[0:len(s)-CNT]
    search=s1[0:len(s1)-CNT]
    s=s1[0:len(s1)-CNT]
    c=c1[0:len(c1)-CNT]


  if ((p1-(l1*p1/100)<=sum(v)/len(v) and sum(v)/len(v)<=p1+(l1*p1/100)) or sum(v)/len(v)>=p1+(l1*p1/100)) :
    return 1
  else:
    return 0

我已經實現了一個 function 應用到 dataframe 但它很慢:

def aggregateListAndOccurrencies(list1,list2):
  final = []
  final_cnt = []
  output = []
  cnt_temp = 0
  while list1:
    elem = list1.pop(0)
    cnt = list2.pop(0)
    i=0
    cnt_temp = cnt
    for item in list1:  
      if pyMATCHSIMILARPN(elem,item,65,20)==1:
        cnt_temp = list2[i]+cnt_temp
        list1.pop(i)
        list2.pop(i)
      i+=1
    final.append(elem)
    final_cnt.append(cnt_temp)

  output.append(final)
  output.append(final_cnt)
  return output

如何在 pandas 中應用它? 有什么建議么?

您可以簡單地對您的ID_1進行分組,然后對ID_2_ListID_OCCURRENCY_LIST列求和:

df.groupby('ID_1').agg({'ID_2_LIST': 'sum', 'ID_OCCURRENCY_LIST': 'sum'})

如果有特定的 function,您希望 groupby 可以使用,那么您可以使用lambda將其添加到 the.agg 中:

df.groupby('ID_1').agg({'ID_2_LIST': 'sum', 'ID_OCCURRENCY_LIST': lambda x: ' '.join(x)})

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM