คำเตือนผู้ใช้ Python Pandas: การเรียงลำดับเนื่องจากแกนที่ไม่ต่อกันไม่ได้อยู่ในแนวเดียวกัน


93

ฉันกำลังฝึกโค้ดและใช้การรวมเฟรมข้อมูลในขณะที่กำลังรับคำเตือนจากผู้ใช้

/usr/lib64/python2.7/site-packages/pandas/core/frame.py:6201: FutureWarning: การเรียงลำดับเนื่องจากแกนที่ไม่ต่อกันไม่ได้อยู่ในแนวเดียวกัน แพนด้าในอนาคตจะเปลี่ยนเป็นไม่จัดเรียงตามค่าเริ่มต้น หากต้องการยอมรับพฤติกรรมในอนาคตให้ส่ง 'sort = True' ในการรักษาพฤติกรรมปัจจุบันและปิดเสียงคำเตือนให้ส่ง sort = False

ในบรรทัดโค้ดเหล่านี้: คุณช่วยหาวิธีแก้ไขคำเตือนนี้ได้ไหม

placement_video = [self.read_sql_vdx_summary, self.read_sql_video_km]
placement_video_summary = reduce(lambda left, right: pd.merge(left, right, on='PLACEMENT', sort=False), placement_video)


placement_by_video = placement_video_summary.loc[:, ["PLACEMENT", "PLACEMENT_NAME", "COST_TYPE", "PRODUCT",
                                                     "VIDEONAME", "VIEW0", "VIEW25", "VIEW50", "VIEW75",
                                                     "VIEW100",
                                                     "ENG0", "ENG25", "ENG50", "ENG75", "ENG100", "DPE0",
                                                     "DPE25",
                                                     "DPE50", "DPE75", "DPE100"]]

# print (placement_by_video)

placement_by_video["Placement# Name"] = placement_by_video[["PLACEMENT",
                                                            "PLACEMENT_NAME"]].apply(lambda x: ".".join(x),
                                                                                     axis=1)

placement_by_video_new = placement_by_video.loc[:,
                         ["PLACEMENT", "Placement# Name", "COST_TYPE", "PRODUCT", "VIDEONAME",
                          "VIEW0", "VIEW25", "VIEW50", "VIEW75", "VIEW100",
                          "ENG0", "ENG25", "ENG50", "ENG75", "ENG100", "DPE0", "DPE25",
                          "DPE50", "DPE75", "DPE100"]]

placement_by_km_video = [placement_by_video_new, self.read_sql_km_for_video]
placement_by_km_video_summary = reduce(lambda left, right: pd.merge(left, right, on=['PLACEMENT', 'PRODUCT'], sort=False),
                                       placement_by_km_video)

#print (list(placement_by_km_video_summary))
#print(placement_by_km_video_summary)
#exit()
# print(placement_by_video_new)
"""Conditions for 25%view"""
mask17 = placement_by_km_video_summary["PRODUCT"].isin(['Display', 'Mobile'])
mask18 = placement_by_km_video_summary["COST_TYPE"].isin(["CPE", "CPM", "CPCV"])
mask19 = placement_by_km_video_summary["PRODUCT"].isin(["InStream"])
mask20 = placement_by_km_video_summary["COST_TYPE"].isin(["CPE", "CPM", "CPE+", "CPCV"])
mask_video_video_completions = placement_by_km_video_summary["COST_TYPE"].isin(["CPCV"])
mask21 = placement_by_km_video_summary["COST_TYPE"].isin(["CPE+"])
mask22 = placement_by_km_video_summary["COST_TYPE"].isin(["CPE", "CPM"])
mask23 = placement_by_km_video_summary["PRODUCT"].isin(['Display', 'Mobile', 'InStream'])
mask24 = placement_by_km_video_summary["COST_TYPE"].isin(["CPE", "CPM", "CPE+"])

choice25video_eng = placement_by_km_video_summary["ENG25"]
choice25video_vwr = placement_by_km_video_summary["VIEW25"]
choice25video_deep = placement_by_km_video_summary["DPE25"]

placement_by_km_video_summary["25_pc_video"] = np.select([mask17 & mask18, mask19 & mask20, mask17 & mask21],
                                                  [choice25video_eng, choice25video_vwr, choice25video_deep])


"""Conditions for 50%view"""
choice50video_eng = placement_by_km_video_summary["ENG50"]
choice50video_vwr = placement_by_km_video_summary["VIEW50"]
choice50video_deep = placement_by_km_video_summary["DPE50"]

placement_by_km_video_summary["50_pc_video"] = np.select([mask17 & mask18, mask19 & mask20, mask17 & mask21],
                                                  [choice50video_eng,
                                                   choice50video_vwr, choice50video_deep])

"""Conditions for 75%view"""

choice75video_eng = placement_by_km_video_summary["ENG75"]
choice75video_vwr = placement_by_km_video_summary["VIEW75"]
choice75video_deep = placement_by_km_video_summary["DPE75"]

placement_by_km_video_summary["75_pc_video"] = np.select([mask17 & mask18, mask19 & mask20, mask17 & mask21],
                                                  [choice75video_eng,
                                                   choice75video_vwr,
                                                   choice75video_deep])

"""Conditions for 100%view"""

choice100video_eng = placement_by_km_video_summary["ENG100"]
choice100video_vwr = placement_by_km_video_summary["VIEW100"]
choice100video_deep = placement_by_km_video_summary["DPE100"]
choicecompletions = placement_by_km_video_summary['COMPLETIONS']

placement_by_km_video_summary["100_pc_video"] = np.select([mask17 & mask22, mask19 & mask24, mask17 & mask21, mask23 & mask_video_video_completions],
                                                          [choice100video_eng, choice100video_vwr, choice100video_deep, choicecompletions])



"""conditions for 0%view"""

choice0video_eng = placement_by_km_video_summary["ENG0"]
choice0video_vwr = placement_by_km_video_summary["VIEW0"]
choice0video_deep = placement_by_km_video_summary["DPE0"]

placement_by_km_video_summary["Views"] = np.select([mask17 & mask18, mask19 & mask20, mask17 & mask21],
                                                   [choice0video_eng,
                                                    choice0video_vwr,
                                                    choice0video_deep])


#print (placement_by_km_video_summary)
#exit()

#final Table

placement_by_video_summary = placement_by_km_video_summary.loc[:,
                             ["PLACEMENT", "Placement# Name", "PRODUCT", "VIDEONAME", "COST_TYPE",
                              "Views", "25_pc_video", "50_pc_video", "75_pc_video","100_pc_video",
                              "ENGAGEMENTS","IMPRESSIONS", "DPEENGAMENTS"]]

#placement_by_km_video = [placement_by_video_summary, self.read_sql_km_for_video]
#placement_by_km_video_summary = reduce(lambda left, right: pd.merge(left, right, on=['PLACEMENT', 'PRODUCT']),
                                       #placement_by_km_video)


#print(placement_by_video_summary)
#exit()
# dup_col =["IMPRESSIONS","ENGAGEMENTS","DPEENGAMENTS"]

# placement_by_video_summary.loc[placement_by_video_summary.duplicated(dup_col),dup_col] = np.nan

# print ("Dhar",placement_by_video_summary)

'''adding views based on conditions'''
#filter maximum value from videos

placement_by_video_summary_new = placement_by_km_video_summary.loc[
    placement_by_km_video_summary.reset_index().groupby(['PLACEMENT', 'PRODUCT'])['Views'].idxmax()]
#print (placement_by_video_summary_new)
#exit()
# print (placement_by_video_summary_new)
# mask22 = (placement_by_video_summary_new.PRODUCT.str.upper ()=='DISPLAY') & (placement_by_video_summary_new.COST_TYPE=='CPE')

placement_by_video_summary_new.loc[mask17 & mask18, 'Views'] = placement_by_video_summary_new['ENGAGEMENTS']
placement_by_video_summary_new.loc[mask19 & mask20, 'Views'] = placement_by_video_summary_new['IMPRESSIONS']
placement_by_video_summary_new.loc[mask17 & mask21, 'Views'] = placement_by_video_summary_new['DPEENGAMENTS']

#print (placement_by_video_summary_new)
#exit()
placement_by_video_summary = placement_by_video_summary.drop(placement_by_video_summary_new.index).append(
    placement_by_video_summary_new).sort_index()

placement_by_video_summary["Video Completion Rate"] = placement_by_video_summary["100_pc_video"] / \
                                                      placement_by_video_summary["Views"]

placement_by_video_final = placement_by_video_summary.loc[:,
                           ["Placement# Name", "PRODUCT", "VIDEONAME", "Views",
                            "25_pc_video", "50_pc_video", "75_pc_video", "100_pc_video",
                            "Video Completion Rate"]]

คำตอบ:


136

tl; dr:

concatและappendจัดเรียงดัชนีแบบไม่ต่อกัน (เช่นคอลัมน์หากคุณกำลังเพิ่มแถว) หากคอลัมน์ไม่ตรงกัน ในแพนด้า 0.23 สิ่งนี้เริ่มสร้างคำเตือน ส่งผ่านพารามิเตอร์sort=Trueเพื่อปิดเสียง ในอนาคตค่าเริ่มต้นจะเปลี่ยนเป็นไม่เรียงลำดับดังนั้นควรระบุอย่างใดอย่างหนึ่งsort=TrueหรือFalseตอนนี้หรือดีกว่า แต่ตรวจสอบให้แน่ใจว่าดัชนีที่ไม่เรียงต่อกันของคุณตรงกัน


คำเตือนใหม่ในแพนด้า 0.23.0 :

ในเวอร์ชันอนาคตของแพนด้าpandas.concat()และDataFrame.append()จะไม่เรียงลำดับแกนที่ไม่ต่อกันอีกต่อไปเมื่อยังไม่ได้จัดแนว ลักษณะการทำงานในปัจจุบันเป็นเช่นเดียวกับก่อนหน้านี้ (เรียงลำดับ) แต่ตอนนี้เตือนออกเมื่อเรียงลำดับไม่ได้ระบุและแกนไม่ใช่เรียงต่อกันจะไม่สอดคล้องใน การเชื่อมโยง

ข้อมูลเพิ่มเติมจากปัญหา github ที่เชื่อมโยงเก่ามากแสดงความคิดเห็นโดย smcinerney :

เมื่อเชื่อมต่อ DataFrames ชื่อคอลัมน์จะได้รับการเรียงลำดับตามตัวอักษรและตัวเลขหากมีความแตกต่างระหว่างกัน หากเหมือนกันใน DataFrames ก็จะไม่ได้รับการจัดเรียง

การเรียงลำดับนี้ไม่มีเอกสารและไม่เป็นที่ต้องการ แน่นอนว่าพฤติกรรมเริ่มต้นไม่ควรเรียงลำดับ

หลังจากเวลาผ่านไประยะหนึ่งพารามิเตอร์sortถูกนำไปใช้pandas.concatและDataFrame.append:

เรียงลำดับ : บูลีนค่าเริ่มต้นไม่มี

จัดเรียงแกนที่ไม่ต่อกันหากยังไม่ได้จัดแนวเมื่อการรวมเป็น 'ด้านนอก' เลิกใช้ค่าเริ่มต้นของการจัดเรียงในปัจจุบันและจะเปลี่ยนเป็นการไม่เรียงลำดับในเวอร์ชันอนาคตของแพนด้า

การเรียงลำดับอย่างชัดเจน = True เพื่อปิดเสียงเตือนและการเรียงลำดับ การเรียงลำดับอย่างชัดเจน = เท็จเพื่อปิดเสียงเตือนและไม่เรียงลำดับ

สิ่งนี้ไม่มีผลเมื่อ join = 'inner' ซึ่งรักษาลำดับของแกนที่ไม่ต่อกันอยู่แล้ว

ดังนั้นหาก DataFrames ทั้งสองมีคอลัมน์เดียวกันในลำดับเดียวกันจะไม่มีคำเตือนและไม่มีการเรียงลำดับ:

df1 = pd.DataFrame({"a": [1, 2], "b": [0, 8]}, columns=['a', 'b'])
df2 = pd.DataFrame({"a": [4, 5], "b": [7, 3]}, columns=['a', 'b'])

print (pd.concat([df1, df2]))
   a  b
0  1  0
1  2  8
0  4  7
1  5  3

df1 = pd.DataFrame({"a": [1, 2], "b": [0, 8]}, columns=['b', 'a'])
df2 = pd.DataFrame({"a": [4, 5], "b": [7, 3]}, columns=['b', 'a'])

print (pd.concat([df1, df2]))
   b  a
0  0  1
1  8  2
0  7  4
1  3  5

แต่ถ้า DataFrames มีคอลัมน์ที่แตกต่างกันหรือคอลัมน์เดียวกันในลำดับที่ต่างกันแพนด้าจะส่งคืนคำเตือนหากไม่มีการตั้งค่าพารามิเตอร์sortอย่างชัดเจน ( sort=Noneเป็นค่าเริ่มต้น):

df1 = pd.DataFrame({"a": [1, 2], "b": [0, 8]}, columns=['b', 'a'])
df2 = pd.DataFrame({"a": [4, 5], "b": [7, 3]}, columns=['a', 'b'])

print (pd.concat([df1, df2]))

FutureWarning: การเรียงลำดับเนื่องจากแกนที่ไม่ต่อกันไม่ได้อยู่ในแนวเดียวกัน

   a  b
0  1  0
1  2  8
0  4  7
1  5  3

print (pd.concat([df1, df2], sort=True))
   a  b
0  1  0
1  2  8
0  4  7
1  5  3

print (pd.concat([df1, df2], sort=False))
   b  a
0  0  1
1  8  2
0  7  4
1  3  5

หาก DataFrames มีคอลัมน์ที่แตกต่างกัน แต่คอลัมน์แรกถูกจัดแนว - คอลัมน์เหล่านี้จะถูกกำหนดให้กันและกันอย่างถูกต้อง (คอลัมน์aและbจากdf1ด้วยaและbจากdf2ในตัวอย่างด้านล่าง) เนื่องจากมีอยู่ทั้ง สำหรับคอลัมน์อื่น ๆ ที่มีอยู่ในหนึ่ง แต่ไม่ใช่ทั้งสอง DataFrames ค่าที่ขาดหายไปจะถูกสร้างขึ้น

สุดท้ายนี้ถ้าคุณผ่านsort=Trueคอลัมน์จะเรียงตามตัวอักษรและตัวเลขคละกัน ถ้าsort=FalseDafaFrame และคอลัมน์ที่สองมีคอลัมน์ที่ไม่ได้อยู่ในคอลัมน์แรกคอลัมน์เหล่านั้นจะถูกต่อท้ายโดยไม่มีการเรียงลำดับ:

df1 = pd.DataFrame({"a": [1, 2], "b": [0, 8], 'e':[5, 0]}, 
                    columns=['b', 'a','e'])
df2 = pd.DataFrame({"a": [4, 5], "b": [7, 3], 'c':[2, 8], 'd':[7, 0]}, 
                    columns=['c','b','a','d'])

print (pd.concat([df1, df2]))

FutureWarning: การเรียงลำดับเนื่องจากแกนที่ไม่ต่อกันไม่ได้อยู่ในแนวเดียวกัน

   a  b    c    d    e
0  1  0  NaN  NaN  5.0
1  2  8  NaN  NaN  0.0
0  4  7  2.0  7.0  NaN
1  5  3  8.0  0.0  NaN

print (pd.concat([df1, df2], sort=True))
   a  b    c    d    e
0  1  0  NaN  NaN  5.0
1  2  8  NaN  NaN  0.0
0  4  7  2.0  7.0  NaN
1  5  3  8.0  0.0  NaN

print (pd.concat([df1, df2], sort=False))

   b  a    e    c    d
0  0  1  5.0  NaN  NaN
1  8  2  0.0  NaN  NaN
0  7  4  NaN  2.0  7.0
1  3  5  NaN  8.0  0.0

ในรหัสของคุณ:

placement_by_video_summary = placement_by_video_summary.drop(placement_by_video_summary_new.index)
                                                       .append(placement_by_video_summary_new, sort=True)
                                                       .sort_index()

21
ฉันไม่ค่อยเข้าใจสิ่งนี้: In a future version of pandas pandas.concat() and DataFrame.append() will no longer sort the non-concatenation axis when it is not already aligned. a คือnon-concatenation axisอะไรและผลลัพธ์จะเป็นอย่างไร? คอลัมน์ a และคอลัมน์ b จะไม่ตรงกันหรือไม่ หรือแค่ลำดับคอลัมน์ต่างกัน?
ข้อเสนอไม่สามารถปฏิเสธ

9
ยังไม่ชัดเจนว่าis not alignedหมายถึงอะไร- คุณสามารถแสดงความคิดเห็นได้หรือไม่?
Mr_and_Mrs_D

1
ฉันเชื่อว่าalignedหมายความว่าระดับในแกนเหมือนกัน: หากมีความแตกต่างใด ๆ พวกเขาจะไม่อีกต่อไปalignedและจะทำให้เกิดพฤติกรรมนี้ (เช่นถ้าระดับแกนเป็น['c','b','a']และ['a'])
Robert Muil

3
@RobertMuil ฉันคิดว่าการใช้คำlevelที่นี่อาจทำให้สับสนlevelได้เนื่องจากมีความหมายเฉพาะสำหรับดาต้าเฟรมของแพนด้าเมื่อมี MultiIndex จากสิ่งที่ฉันเข้าใจalignedในบริบทนี้หมายถึงลำดับของดัชนีแถว / คอลัมน์ ดังนั้นหากลำดับดัชนีของแกนที่ไม่เรียงต่อกันแตกต่างกันสำหรับสองเฟรมของคุณคุณสามารถระบุได้ว่าจะรักษาลำดับในเฟรมแรกที่ส่งผ่านไปหรือไม่และเรียงลำดับเฟรมที่สองให้ตรงกันหรือจัดเรียงดัชนีของทั้งสองเฟรมก่อนที่จะเรียงต่อกัน นี่เป็นพื้นที่ที่สับสนสำหรับฉันเช่นกันดังนั้นการแก้ไขยินดีต้อนรับ!
24

tuple(df1.columns) == tuple(df2.columns)คอลัมน์มีความสอดคล้องเมื่อ แกนที่ไม่ต่อกันคือแกน (แถวหรือคอลัมน์) ขนานกับรอยต่อซึ่งมีการต่อเฟรมข้อมูลเข้าด้วยกัน
BallpointBen

107

คำตอบของ jezrael นั้นดี แต่ไม่ได้ตอบคำถามที่ฉันมี: การตั้งค่าสถานะ "sort" ผิดจะทำให้ข้อมูลของฉันเสียหายหรือไม่ คำตอบคือ "ไม่" คุณก็ไม่เป็นไร

from pandas import DataFrame, concat

a = DataFrame([{'a':1,      'c':2,'d':3      }])
b = DataFrame([{'a':4,'b':5,      'd':6,'e':7}])

>>> concat([a,b],sort=False)
   a    c  d    b    e
0  1  2.0  3  NaN  NaN
0  4  NaN  6  5.0  7.0

>>> concat([a,b],sort=True)
   a    b    c  d    e
0  1  NaN  2.0  3  NaN
0  4  5.0  NaN  6  7.0

อะไรเรียงลำดับหรือไม่เรียงลำดับกันแน่?
เบ็น

2
@ เบ็นคำเตือนจะปรากฏขึ้นเมื่อลำดับคอลัมน์แตกต่างกันระหว่างดาต้าเฟรม ดังที่คุณสามารถดูได้ว่า sort = True หรือไม่ดังนั้นคอลัมน์หลังจากการเรียงต่อกันจะเรียงตามตัวอักษร
MP23

ในตัวอย่างนี้ไม่ได้ แต่ถ้าคุณเชื่อมต่อหลาย Series หรือ DataFrames กับ DatetimeIndex แถวจะไม่อยู่ในลำดับเวลาอีกต่อไป ในทางเทคนิคข้อมูลจะไม่ยุ่งเหยิง แต่ผลลัพธ์ของคุณอาจอ่านยากกว่า
hugovdberg
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.