आप पंडों डेटाफ्रेम को कई कॉलमों से कैसे फ़िल्टर करते हैं


100

किसी एकल स्तंभ द्वारा डेटाफ़्रेम (df) फ़िल्टर करने के लिए, यदि हम पुरुष और महिलाओं के साथ डेटा पर विचार करते हैं, तो हम कर सकते हैं:

males = df[df[Gender]=='Male']

प्रश्न 1 - लेकिन क्या होगा यदि डेटा कई वर्षों तक फैला रहे और मैं केवल 2014 के लिए पुरुषों को देखना चाहता था?

अन्य भाषाओं में मैं कुछ ऐसा कर सकता हूं:

if A = "Male" and if B = "2014" then 

(इसके अलावा मैं ऐसा करना चाहता हूं और नई डेटाफ्रेम ऑब्जेक्ट में मूल डेटाफ्रेम का सबसेट प्राप्त कर सकता हूं)

प्रश्न 2. मैं इसे एक लूप में कैसे करूं, और वर्ष और लिंग के प्रत्येक अनूठे सेट के लिए एक डेटाफ्रेम ऑब्जेक्ट बनाता हूं (अर्थात: 2013-पुरुष, 2013-महिला, 2014-पुरुष और 2014-महिला

for y in year:

for g in gender:

df = .....

क्या आप इसे फ़िल्टर करना चाहते हैं या इसे समूहित करना चाहते हैं? यदि आप वर्ष और लिंग के प्रत्येक अद्वितीय सेट के लिए एक अलग DataFrame बनाना चाहते हैं, तो देखें groupby
ब्रेनबर्न

1
यह जवाब पांडों में बूलियन इंडेक्सिंग और तार्किक ऑपरेटरों का एक व्यापक अवलोकन देता है।
सीएस 95 95

जवाबों:


172

&ऑपरेटर का उपयोग करना , उप-कथनों को साथ रखना न भूलें ():

males = df[(df[Gender]=='Male') & (df[Year]==2014)]

dictलूप के लिए उपयोग में अपने डेटाफ्रेम को स्टोर करने के लिए:

from collections import defaultdict
dic={}
for g in ['male', 'female']:
  dic[g]=defaultdict(dict)
  for y in [2013, 2014]:
    dic[g][y]=df[(df[Gender]==g) & (df[Year]==y)] #store the DataFrames to a dict of dict

संपादित करें:

आपके लिए एक डेमो getDF:

def getDF(dic, gender, year):
  return dic[gender][year]

print genDF(dic, 'male', 2014)

महान उत्तर zhangxaochen - क्या आप अपने जवाब को नीचे दिखा सकते हैं कि आप एक लूप के लिए कैसे कर सकते हैं, जो डेटाफ्रेम (वर्ष और लिंग डेटा के साथ) बनाता है, लेकिन उन्हें एक शब्दकोश में जोड़ता है, ताकि बाद में उन्हें मेरी getDF विधि द्वारा एक्सेस किया जा सके? defDF (तानाशाही, कुंजी) को हराएं: तानाशाह लौटें [कुंजी]
योशिसरी

@yoshiserry क्या keyअपने में की तरह getDF? एक एकल पैरामीटर या कुंजियों का टपल? विशिष्ट plz;)
zhangxaochen

नमस्ते यह एक कुंजी है, बस एक शब्द है, जो लिंग (पुरुष, या महिला) या वर्ष (13, 14) के अनुरूप होगा। आपको नहीं पता था कि आपके पास कुंजी का एक टपल हो सकता है। क्या आप ऐसा कब और कैसे करेंगे इसका एक उदाहरण साझा कर सकते हैं?
योशियरी

क्या आप इस प्रश्न पर भी नज़र डाल सकते हैं। मुझे ऐसा लगता है कि आप इसका जवाब दे सकते हैं। पांडा डेटाफ़्रेम से फिर से संबंधित है। stackoverflow.com/questions/22086619/…
yoshiserry

1
ध्यान दें कि Genderऔर Yearदोनों तार, यानी, 'Gender'और होना चाहिए 'Year'
स्टीवन सी। हॉवेल

22

अधिक सामान्य बूलियन कार्यों के लिए जिन्हें आप एक फिल्टर के रूप में उपयोग करना चाहते हैं और जो एक से अधिक कॉलम पर निर्भर करते हैं, आप उपयोग कर सकते हैं:

df = df[df[['col_1','col_2']].apply(lambda x: f(*x), axis=1)]

जहाँ f एक ऐसा फ़ंक्शन है, जो col_1 और col_2 से तत्वों की प्रत्येक जोड़ी (X1, x2) पर लागू होता है और आपके द्वारा (X1, x2) किसी भी शर्त के आधार पर True या False लौटाता है।


11

पांडा 0.13 से शुरू करें , यह सबसे कारगर तरीका है।

df.query('Gender=="Male" & Year=="2014" ')

1
स्वीकृत उत्तर की तुलना में यह अधिक कुशल क्यों होना चाहिए?
बाउंसर

@ बाउंसर सिर्फ उच्च मत वाले उत्तर के खिलाफ इसे सत्यापित करें।
redreamality

4
इस उत्तर को
नार्देस

8

मामले में किसी को आश्चर्य होता है कि फ़िल्टर करने का तेज़ तरीका क्या है (स्वीकृत उत्तर या @redreamality से)

import pandas as pd
import numpy as np

length = 100_000
df = pd.DataFrame()
df['Year'] = np.random.randint(1950, 2019, size=length)
df['Gender'] = np.random.choice(['Male', 'Female'], length)

%timeit df.query('Gender=="Male" & Year=="2014" ')
%timeit df[(df['Gender']=='Male') & (df['Year']==2014)]

100,000 पंक्तियों के लिए परिणाम:

6.67 ms ± 557 µs per loop (mean ± std. dev. of 7 runs, 100 loops each)
5.54 ms ± 536 µs per loop (mean ± std. dev. of 7 runs, 100 loops each)

10,000,000 पंक्तियों के लिए परिणाम:

326 ms ± 6.52 ms per loop (mean ± std. dev. of 7 runs, 1 loop each)
472 ms ± 25.1 ms per loop (mean ± std. dev. of 7 runs, 1 loop each)

इसलिए परिणाम आकार और डेटा पर निर्भर करते हैं। मेरे लैपटॉप पर, query()500k पंक्तियों के बाद तेज हो जाता है। इसके अलावा, स्ट्रिंग खोज में Year=="2014"एक अनावश्यक ओवरहेड है ( Year==2014तेज है)।


1
हालाँकि, मुझे लगता है कि queryसिंटैक्स nter और SQL के करीब है, जो डेटा के लिए अच्छा बनाता है। केक पर
चरी

1

आप उपयोग कर अपने खुद फिल्टर समारोह बना सकते हैं queryमें pandas। यहां आपके पास dfसभी kwargsमापदंडों द्वारा परिणामों को फ़िल्टर करना है। kwargsअपने लिए फ़िल्टर फ़ंक्शन प्राप्त करने के लिए कुछ सत्यापनकर्ताओं ( फ़िल्टरिंग) को जोड़ना न भूलें df

def filter(df, **kwargs):
    query_list = []
    for key in kwargs.keys():
        query_list.append(f'{key}=="{kwargs[key]}"')
    query = ' & '.join(query_list)
    return df.query(query)

सुरुचिपूर्ण समाधान के लिए धन्यवाद! मुझे लगता है कि यह बाकी सभी में से सबसे अच्छा है। यह फ़ंक्शन के रूप में होने की बहुमुखी प्रतिभा के साथ क्वेरी का उपयोग करने की दक्षता को जोड़ती है।
एक मेरि जूल

0

आप (या बदलने के लिए ) np.logical_andऑपरेटर का उपयोग करके कई कॉलम (दो से अधिक) से फ़िल्टर कर सकते हैं&np.logical_or|

यहां एक उदाहरण फ़ंक्शन है जो काम करता है, यदि आप कई क्षेत्रों के लिए लक्ष्य मान प्रदान करते हैं। आप इसे विभिन्न प्रकार के फ़िल्टरिंग और whatnot के लिए अनुकूलित कर सकते हैं:

def filter_df(df, filter_values):
    """Filter df by matching targets for multiple columns.

    Args:
        df (pd.DataFrame): dataframe
        filter_values (None or dict): Dictionary of the form:
                `{<field>: <target_values_list>}`
            used to filter columns data.
    """
    import numpy as np
    if filter_values is None or not filter_values:
        return df
    return df[
        np.logical_and.reduce([
            df[column].isin(target_values) 
            for column, target_values in filter_values.items()
        ])
    ]

उपयोग:

df = pd.DataFrame({'a': [1, 2, 3, 4], 'b': [1, 2, 3, 4]})

filter_df(df, {
    'a': [1, 2, 3],
    'b': [1, 2, 4]
})
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.