第七色在线视频,2021少妇久久久久久久久久,亚洲欧洲精品成人久久av18,亚洲国产精品特色大片观看完整版,孙宇晨将参加特朗普的晚宴

為了賬號安全,請及時綁定郵箱和手機(jī)立即綁定
已解決430363個問題,去搜搜看,總會有你想問的

使用 pandas merge_asof() 識別范圍關(guān)系

使用 pandas merge_asof() 識別范圍關(guān)系

回首憶惘然 2022-10-06 16:07:10
給定以下兩個表示范圍的數(shù)據(jù)框:df1 =  start   end0   200   3001   600   9002   950  1050df2 =  start   end0   350   5501   650   8002   900  1100它們可以這樣表示:df1  [200 300]            [600    900] [950 1050]df2            [350  550]   [650 800] [900   1100]我的任務(wù)是確定范圍df1和df2范圍之間的四種不同類型的關(guān)系:df2的子集df1df2 [650 800]的子集df1 [600    900]df2的超集df1df2 [900   1100]的超集df1 [950 1050]df2之后df1(最近鄰,不包括子集/超集)df2 [350  550]后df1 [200 300]df2 [900   1100]后df1 [600    900]df2之前df1(最近的鄰居,不包括子集/超集)df2 [350  550]前df1 [600    900]df2 [650 800]前df1 [950 1050]我正在嘗試使用merge_asof()從這個答案中學(xué)到的東西,但由于超集/子集關(guān)系添加的復(fù)雜性,它不起作用,例如:# Create "before" conditiondf_before = pd.merge_asof(    df2.rename(columns={col:f'before_{col}' for col in df2.columns}).sort_values('before_end'),    df1.assign(before_end=lambda x: x['end']).sort_values('before_end'),    on='before_end',    direction='forward').query('end > before_end')print(df_before)輸出:  before_start  before_end  start    end0          350         550  600.0  900.01          650         800  600.0  900.0目標(biāo)輸出:  before_start  before_end  start     end0          350         550  600.0   900.01          650         800  950.0  1050.0問題是pd.merge_asof(    df2.rename(columns={col:f'before_{col}' for col in df2.columns}).sort_values('before_end'),    df1.assign(before_end=lambda x: x['end']).sort_values('before_end'),    on='before_end',    direction='forward')df1.end在 800 之后找到最接近的df2 [650 800],即df1 [600    900]:  before_start  before_end  start    end0          350         550  600.0  900.01          650         800  600.0  900.02          900        1100    NaN    NaN是否可以merge_asof()根據(jù)特定條件查找最接近的值,例如“df1.end僅當(dāng)df1.start該范圍大于 800(在本例中為 950)時才查找最近的值”?有了這種復(fù)雜程度,也許還有另一個更適合這項任務(wù)的功能?筆記:中的范圍df1可以相互重疊,但絕不相同。中的范圍df2可以相互重疊,但絕不相同。df1并且df2每行有超過 200k 行。df1并且df2有不同的行數(shù)。
查看完整描述

1 回答

?
阿晨1998

TA貢獻(xiàn)2037條經(jīng)驗 獲得超6個贊

可以pd.merge_asof用來查找之前和之后的選項。


before_df = pd.merge_asof(df1, df2, left_on='start', right_on='end', suffixes=['', '_before'])

before_df

#    start   end  start_before  end_before

# 0    200   300           NaN         NaN

# 1    600   900         350.0       550.0

# 2    950  1050         650.0       800.0


after_df = pd.merge_asof(df2, df1, left_on='start', right_on='end', suffixes=['_after', ''])

#    start_after  end_after  start  end

# 0          350        550    200  300

# 1          650        800    200  300

# 2          900       1100    600  900

但是要使其工作或子集和超集計算并不容易。對于那些人,我會爭取這種可以一次性工作的算法。


def range_intersect(lh_ranges, rh_ranges): 

    all_ranges = sorted(

        [(b, e, 'lh') for b, e in lh_ranges] +

        [(b, e, 'rh') for b, e in rh_ranges]

    ) 


    res = [] 

    max_b, max_e = None, None 

    for b, e, which in all_ranges: 

        if which == 'rh': 

            if max_e is None or e > max_e: 

                max_b, max_e = b, e 

        elif max_e is not None and e <= max_e: 

            res.append((b, e, max_b, max_e)) 


    return res

這會發(fā)現(xiàn) 的元素是lh中元素的子集rh。要查找超集,可以反向運(yùn)行。為簡單起見,它采用范圍列表而不是DataFrames。轉(zhuǎn)換很簡單。


lh = df1.to_dict('split')['data']

rh = df2.to_dict('split')['data']


lh

# [[200, 300], [600, 900], [950, 1050]]


rh                                                                                                                                                                                                                                  

# [[350, 550], [650, 800], [900, 1100]]

在那之后,DataFrame你想要的結(jié)果只是幾個合并。


# Compute supersets, then run in reverse to get the subsets.

superset_df = pd.DataFrame(range_intersect(lh, rh), columns=['start', 'end', 'start_superset', 'end_superset'])

subset_df = pd.DataFrame(range_intersect(rh, lh), columns=['start_subset', 'end_subset', 'start', 'end'])


# Merge all the results together.

result = df1.merge(subset_df, how='left').merge(superset_df, how='left').merge(before_df, how='left').merge(after_df, how='left')


# The reversed operations, after and subset, can have many matches in df1.

result.drop_duplicates(['start', 'end'])

#    start   end  start_subset  end_subset  start_superset  end_superset  start_before  end_before  start_after  end_after

# 0    200   300           NaN         NaN             NaN           NaN           NaN         NaN        350.0      550.0

# 2    600   900         650.0       800.0             NaN           NaN         350.0       550.0        900.0     1100.0

# 3    950  1050           NaN         NaN           900.0        1100.0         650.0       800.0          NaN        NaN



查看完整回答
反對 回復(fù) 2022-10-06
  • 1 回答
  • 0 關(guān)注
  • 216 瀏覽
慕課專欄
更多

添加回答

舉報

0/150
提交
取消
微信客服

購課補(bǔ)貼
聯(lián)系客服咨詢優(yōu)惠詳情

幫助反饋 APP下載

慕課網(wǎng)APP
您的移動學(xué)習(xí)伙伴

公眾號

掃描二維碼
關(guān)注慕課網(wǎng)微信公眾號