我有一個s包含串列條目的系列,例如[1, 2, 3, NaN, NaN]或[4, 5]。這些串列可能包含 NaN 作為最后幾個元素,我想洗掉本系列中包含 NaN 的所有條目。到目前為止,我已經使用s.transform(lambda x: np.nan if np.isnan(x).any() else x).dropna()了 ,但這僅在 2100 萬行上就需要一分鐘多的時間,而且我最終計劃對數百億行進行此操作,所以我需要一些快速的東西。謝謝!
需要強調的是,該系列中的每個條目都是一個串列,因此我不能只使用pd.dropna(),因為沒有 NaN 條目,因為它們本身就是串列。我想洗掉 CONTAIN NaN 的串列(條目)。這就是這個系列的s樣子:pd.Series([1, 2, 3, NaN, NaN], [4, 5]...).
uj5u.com熱心網友回復:
假設這個輸入:
from numpy import NaN
s = pd.Series([[1, 2, 3, NaN, NaN], [4, 5]])
您可以使用:
s2 = s[s.explode().notna().groupby(level=0).all()]
或者,使用串列理解:
s2 = s[[pd.Series(x).notna().all() for x in s]]
輸出:
1 [4, 5]
dtype: object
uj5u.com熱心網友回復:
您可以為展開的資料框識別所有等于的索引位置,NaN然后可以過濾那些不在索引陣列中的資料框:
ser = pd.DataFrame(data={"col": [[1, 2, 3, np.nan, np.nan], [3, 4, 5], [3, 9], [np.nan, 10]]})['col']
ser_exploded = ser.explode()
ser[~ser.index.isin(np.unique(ser_exploded[ser_exploded.isna()].index))]
--------------------------------------
1 [3, 4, 5]
2 [3, 9]
Name: col, dtype: object
--------------------------------------
uj5u.com熱心網友回復:
一個替代方案multiprocessing:
import pandas as pd
import numpy as np
import multiprocessing as mp
import time
def check_nan(s):
return s.explode().isna().groupby(level=0).max()
if __name__ == '__main__': # Do not remove this line! Mandatory
# Setup a minimal reproducible example
N = 10_000_000
s = pd.Series([[1, 2, 3, np.NaN, np.NaN], [4, 5]]).repeat(N)
s = s.sample(frac=1, ignore_index=True)
CHUNKSIZE = 10_000
start = time.time()
with mp.Pool(mp.cpu_count() - 1) as p:
results = p.map(check_nan, (s[i:i CHUNKSIZE] for i in range(0, len(s), CHUNKSIZE)))
m = pd.concat(results)
s = s[~m]
end = time.time()
print(f"Elapsed time: {end - start:.2f} seconds")
對于 20,000,000 條記錄:
[...]$ python mp.py
Elapsed time: 1.58 seconds
注意:沒有mp,執行時間為 6.07 秒:
start = time.time()
m = s.explode().isna().groupby(level=0).max()
s1 = s[~m]
end = time.time()
print(f"Elapsed time: {end - start:.2f} seconds")
uj5u.com熱心網友回復:
您將其轉換為 DF,爆炸,然后洗掉所有 NA,最后將其連接回串列,作為原始系列
s.to_frame().reset_index().explode(0).dropna().groupby('index')[0].agg(list)
輸入
0 [1, 2, 3, nan, nan]
1 [4, 5]
結果
0 [1, 2, 3]
1 [4, 5]
uj5u.com熱心網友回復:
如果我正確理解了您的問題,那么使用測驗 NaN 值的掩碼過濾行應該可以作業
import pandas as pd
from numpy import nan as NaN
s = pd.Series([[1, 2, 3, NaN, NaN], [4, 5]])
s = s[~s.apply(lambda list1: any(pd.isna(x) for x in list1))]
print(s)
1 [4, 5]
dtype: object
轉載請註明出處,本文鏈接:https://www.uj5u.com/houduan/493904.html
上一篇:將多個元素移動到新的div
下一篇:如何匯出異步函式的輸出?[復制]
