قسّم، طبّق، اجمع
تطلب أسئلة كثيرة رقمًا لكل مجموعة: تعرض كل قطاع ومتوسط عائد كل استراتيجية وعدد الصفقات في اليوم. والنمط واحد دائمًا، قسّم-طبّق-اجمع (split-apply-combine). فـdf.groupby("sector") تقسم الصفوف إلى مجموعات بحسب قيم عمود، ويُطبَّق تجميع مثل .sum() على كل مجموعة، وتجمع pandas النتائج في جدول واحد مفهرس بمفاتيح المجموعات. وبدونها كنت ستكتب حلقة بقاموس من المجاميع الجارية؛ وبها تتسع المسألة كلها في سطر: df.groupby("sector")["value"].sum().
import pandas as pd
df = pd.DataFrame({
"symbol": ["AAPL", "MSFT", "GOOG", "TSLA", "F"],
"sector": ["tech", "tech", "tech", "auto", "auto"],
"value": [36850.0, 20510.0, 51300.0, 30120.0, 9000.0],
"ret": [0.012, -0.004, 0.021, 0.03, -0.01],
})
print(df.groupby("sector")["value"].sum())
# sector
# auto 39120.0
# tech 108660.0
# Name: value, dtype: float64
print(df.groupby("sector").size().to_dict()) # {'auto': 2, 'tech': 3} rows per group
print(df.groupby("sector")["ret"].mean().round(4).to_dict()) # {'auto': 0.01, 'tech': 0.0097}عدة ملخصات دفعة واحدة مع agg
تحسب .agg() عدة ملخصات في تمريرة واحدة وتتيح تسمية أعمدة النتيجة: df.groupby("sector").agg(count=("value", "size"), mean_return=("ret", "mean"), max_value=("value", "max")). كل وسيط مسمّى هو اسم العمود الجديد، ويقول الصف (tuple) أي عمود يُقرأ وأي دالة تُطبَّق ("sum" و"mean" و"min" و"max" و"std" و"size" و"first"...). ويمكنك التجميع بعدة أعمدة معًا groupby(["sector", "day"]) فتحصل على نتيجة بفهرس من مستويين. وتُرتَّب مفاتيح المجموعات افتراضيًا، وتُسقَط الصفوف التي مفتاحها مفقود (NaN).
import pandas as pd
df = pd.DataFrame({
"symbol": ["AAPL", "MSFT", "GOOG", "TSLA", "F"],
"sector": ["tech", "tech", "tech", "auto", "auto"],
"value": [36850.0, 20510.0, 51300.0, 30120.0, 9000.0],
"ret": [0.012, -0.004, 0.021, 0.03, -0.01],
})
summary = df.groupby("sector").agg(
count=("value", "size"),
mean_return=("ret", "mean"),
max_value=("value", "max"),
)
print(summary)
# count mean_return max_value
# sector
# auto 2 0.010000 30120.0
# tech 3 0.009667 51300.0
print(df.groupby("sector")["ret"].agg(["min", "max"])) # a list of function names
# min max
# sector
# auto -0.010 0.030
# tech -0.004 0.021transform: إحصاء المجموعة على كل صف
يختزل التجميع كل مجموعة إلى صف. أما transform فيحتفظ بالشكل الأصلي: يحسب إحصاء المجموعة ويكرره على كل صف فيها محاذيًا للفهرس الأصلي. فهو أداة «قيمة صف مقارنةً بمجموعته»: حصة مركز في قطاعه هي df["value"] / df.groupby("sector")["value"].transform("sum")، والتمركز حول المتوسط داخل مجموعة هو x - x.groupby(g).transform("mean"). ولانتقاء صفوف كاملة لكل مجموعة، كأفضل أداء في كل قطاع، استخدم idxmax() للحصول على وسم الفهرس لأقصى قيمة في كل مجموعة ثم اختر تلك الصفوف بـ.loc.
import pandas as pd
df = pd.DataFrame({
"symbol": ["AAPL", "MSFT", "GOOG", "TSLA", "F"],
"sector": ["tech", "tech", "tech", "auto", "auto"],
"value": [36850.0, 20510.0, 51300.0, 30120.0, 9000.0],
"ret": [0.012, -0.004, 0.021, 0.03, -0.01],
})
totals = df.groupby("sector")["value"].transform("sum") # one value per original row
print(totals.tolist()) # [108660.0, 108660.0, 108660.0, 39120.0, 39120.0]
print((df["value"] / totals).round(3).tolist()) # [0.339, 0.189, 0.472, 0.77, 0.23]
best = df.loc[df.groupby("sector")["ret"].idxmax()].set_index("sector")[["symbol", "ret"]]
print(best)
# symbol ret
# sector
# auto TSLA 0.030
# tech GOOG 0.021import pandas as pd
t = pd.DataFrame({
"day": ["mon", "mon", "tue", "tue"],
"sector": ["tech", "auto", "tech", "tech"],
"value": [1.0, 2.0, 3.0, 4.0],
})
# Two keys give a two-level index
print(t.groupby(["day", "sector"])["value"].sum())
# day sector
# mon auto 2.0
# tech 1.0
# tue tech 7.0
# Name: value, dtype: float64
# reset_index() turns the keys back into ordinary columns
print(t.groupby(["day", "sector"])["value"].sum().reset_index())
# day sector value
# 0 mon auto 2.0
# 1 mon tech 1.0
# 2 tue tech 7.0for name, group in df.groupby("sector"): وهذا مقبول لطباعة أو رسم بضع مجموعات، لكن للأرقام تكون التجميعات المدمجة وtransform أقصر وأسرع بكثير من حلقة بايثون أو apply مع دالة. افحص فهرس النتيجة (مفاتيح المجموعات، مرتّبة عادة) وأنواعها، وتذكّر أن size تعدّ الصفوف بينما count تعدّ القيم غير المفقودة.df.groupby(key)[col].sum()(أوmeanأوmaxأوsize...): قيمة لكل مجموعة مفهرسة بالمفاتيح..agg(name=(column, function), ...)تنتج عدة ملخصات مسمّاة دفعة واحدة.transformيحافظ على عدد الصفوف (الحصص والتمركز)؛ وidxmaxمع.locيختاران صفوفًا كاملة لكل مجموعة.
التالي: دمج الجداول وربطها، الجمع بين جداول تتشارك مفتاحًا، مثل الأسعار والبيانات المرجعية.
المختبر: ما الذي يُقيَّم
- اجمع تعرّض كل قطاع باستخدام
total_by_sector25 نقطة - لخّص كل قطاع في جدول واحد باستخدام
summary_by_sector25 نقطة - قِس كل مركز مقابل قطاعه باستخدام
share_of_sector25 نقطة - اختر الأفضل أداءً في كل قطاع باستخدام
best_per_sector25 نقطة