يخلط الكثير من الناس بين سياق الصف (Row Context) وسياق التصفية (Filter Context) بسبب التشابه في التسمية، حيث إن سياق التصفية يتم إنشاؤه من “صفوف” جدول بصري في كثير من الحالات. لاستكشاف سياق الصف بمزيد من التفصيل، تحقق من المقال أدناه.
سياق الصف (Row Context):
يشير سياق الصف في DAX إلى سياق الصف الحالي ضمن جدول البيانات، حيث يتم تنفيذ العمليات الحسابية بشكل تكراري على كل صف—ويحدث ذلك تلقائيًا في الأعمدة المحسوبة (Calculated Columns) وداخل صيغ محددة (Specific Formulas) في المقاييس (Measures).
ملاحظات يجب أخذها في الاعتبار:
- الأعمدة المحسوبة تحتوي على سياق صف مدمج تلقائيًا.
- المقاييس لا تحتوي على سياق صف مدمج، ولكن يمكنك إدخال سياق صف باستخدام دوال مثل:
- SUMX()
- MAXX()
- MINX()
سيتم شرح الفروقات بين الأعمدة المحسوبة والمقاييس بالتفصيل في مقال آخر.
الشرح من خلال سرد قصة صغيرة:

إنه “يوم معرفة زملاء الصف”، وكانت الحماسة تعم أرجاء الفصل بينما عرض الطلاب أغراضهم المفضلة بكل فخر. عرضت سارة حرباءها الملونة، وتباهى ماكس بلوح التزلج الخاص به ، بينما جلس فهد بابتسامة عريضة على وجهه، ينتظر أن يسأله أحدهم عن مجموعة الكرات الزجاجية المبهرة المنتشرة على مكتبه.
لفتت مجموعة الكرات الزجاجية الملونة أنظار جميع الطلاب في المدرسة، وحاول بعضهم حتى سرقة كرة أو اثنتين، لكن فهد لم يكن متساهلاً بشأن مجموعته، وأصر على أن من يرغب في الحصول على كرة يجب أن يذكر لونها وحجمها، وسيحضرها فهد ويبيعها له خلال وقت الاستراحة.
أصبح عمل فهد مزدهرًا، وسرعان ما صار المرجع الأول لشراء الكرات الزجاجية بين طلاب الصف السادس. ولكن مع تزايد الطلبات ليلًا ونهارًا، لم يكن أمامه خيار سوى تتبعها في ملف Excel.

كان فهد يريد أن يستخدم الأرباح لشراء رف خزفي لعرض مجموعته من الكرات الزجاجية، لكنه أولاً أراد أن يحدد من هو أكبر زبون لديه وما هي أكبر طلبية حصل عليها، لكي يكتب رسالة شخصية لكلٍ منهما يشكرهما فيها على منحه الفرصة للارتقاء بهوايته إلى المستوى التالي.
قرأ فهد الملاحظات، ولهذا كان يعلم أن هناك طريقتين يمكنه من خلالهما التعامل مع هذه المشكلة لإيجاد الحل، إما باستخدام:
الأعمدة المحسوبة (Calculated Columns)
القياسات (Measures)
الحل الأول: استخدام القياسات (Measures)
كما هو مذكور في الملاحظات، فإن القياسات لا تمتلك سياق صف (Row Context) خاص بها، ويجب إدخاله باستخدام دالة. وبما أن فهد يريد حساب مجموع الأرباح التي حصل عليها من كل زبون من زبائنه، فسيستخدم دالة SUMX.
مقياس الربح = SUMX(
-- الجدول المستخدم لأنشاء سياق الصف
'بيانات بيع الكرات الزجاجية',
-- العملية الحسابية المطبقة على كل صف في الجدول
('بيانات بيع الكرات الزجاجية'[سعر البيع]
-'بيانات بيع الكرات الزجاجية'[التكلفة])*
'بيانات بيع الكرات الزجاجية'[العدد]
)
لحساب الربح، يقوم فهد بطرح تكلفة الكرة الزجاجية من سعر البيع، ثم يضرب الناتج في عدد الكرات الزجاجية المدرجة في ذلك الصف. بعد ذلك، تقوم دالة SUMX بجمع جميع النتائج المختلفة التي تم حسابها لكل صف بناءً على سياق الصف الحالي.

على سبيل المثال، استنادًا إلى عينة البيانات الموضحة أعلاه، ستقوم دالة SUMX بالتكرار عبر الجدول كما يلي:
((0.7 – 0.35) * 6) + ((0.7 – 0.35) * 1) + ((0.7 – 0.35) * 7) …. حتى يتم تطبيق الصيغة على كل صف في الجدول.
القياس (Measure) لا ينشئ عمودًا جديدًا في جدول فهد ولا يشغل مساحة، ويتم حسابه فقط عند إضافته إلى تصور (Visualization) تم إنشاؤه، لكن سنتحدث عن ذلك لاحقًا.

أنشأ فهد تصورين (Visuals):
الأول يحتوي على عمود العميل والقياس الخاص بالربح (مقياس الربح) لمعرفة من هو أكبر عميل لديه.
والثاني يحتوي على أعمدة رقم الطلب (رقم الطلب) والعميل، بالإضافة إلى قياس الربح (مقياس الربح) لمعرفة من هو صاحب أكبر طلبية لديه.
يتم تقسيم القيم في التصورات حسب العميل أو حسب (رقم الطلب والعميل) وذلك بسبب سياق التصفية في
Power BI (Filter Context). لمزيد من المعلومات حول ذلك، يمكنك الرجوع إلى:
Power BI: DAX Filter Context بالعربية
الحل الثاني: استخدام الأعمدة المحسوبة (Calculated Columns)
كما هو مذكور في الملاحظات، فإن الأعمدة المحسوبة تمتلك سياق صف مدمج (Row Context)، لذلك فالإجابة هنا مباشرة وواضحة.
عامود الربح =
-- سياق صف مدمج و خفي
('بيانات بيع الكرات الزجاجية'[سعر البيع]
-'بيانات بيع الكرات الزجاجية'[التكلفة])
* 'بيانات بيع الكرات الزجاجية'[العدد]
سياق الصف (Row Context) في العمود المحسوب يسمح بتطبيق الصيغة المذكورة على كل صف في الجدول.

سيتم تخزين العمود المحسوب في جدول فهد، مما سيؤدي إلى زيادة حجم نموذج البيانات، لكن سنتحدث عن ذلك أكثر لاحقًا.

حل فهد مشكلته باستخدام طريقتين مختلفتين، وتأكد من أن:
محمد كان أكبر زبون لديه، حيث أنفق ما مجموعه ٧٣.٨٠ جنيها.
سارة كانت صاحبة أكبر طلبية منفردة بقيمة ١٦.٤٠ جنيها.
أخذ فهد يومًا إجازة من أبحاثه المكثفة حول الكرات الزجاجية ليكتب رسالة شكر دافئة لكلٍ من محمد وسارة ليُظهر امتنانه وتقديره لمساعدتهما.
التفسير باستخدام مكتبة pandas في python
import pandas as pd
إطار_البيانات = pd.read_csv("بيانات بيع الكرات الزجاجية.csv")
# إنشاء عمود جديد للأرباح لحساب ربح كل صف.
إطار_البيانات ["الأرباح"] =
(إطار_البيانات ["سعر البيع"]-إطار_البيانات ["التكلفة"])
*إطار_البيانات ["العدد"]
'''
التجميع باستخدام العميل فقط،
وتجميع النتائج بناءً على مجموع عمود الأرباح ،
ثم ترتيب النتائج حسب عمود الأرباح بشكل تنازلي.
'''
الأرباح_حسب_العميل = إطار_البيانات .groupby(by="العميل").
agg({"الأرباح":"sum"}).sort_values(by="الأرباح", ascending=False)
print(الأرباح_حسب_العميل)
'''
التجميع باستخدام رقم الطلب والعميل ،
وتجميع النتائج بناءً على مجموع عمود الأرباح ،
ثم ترتيب النتائج حسب عمود الأرباح بشكل تنازلي.
'''
الأرباح_حسب_العميل_و_رقم_الطلب = إطار_البيانات .
groupby(by=["رقم الطلب","العميل"]).
agg({"الأرباح":"sum"}).sort_values(by="الأرباح", ascending=False)
print(الأرباح_حسب_العميل_و_رقم_الطلب)
التفسير باستخدام SQL
-- أكبر عميل
-- اختر اسم العميل والربح المحسوب، ثم قم بتجميع البيانات حسب العميل
-- ورتب النتائج حسب ربح العميل بشكل تنازلي
SELECT
العميل,
SUM((سعر_البيع - التكلفة) * العدد) AS
الأرباح_حسب_العميل
FROM marbles_fahad
GROUP BY العميل
ORDER BY الأرباح_حسب_العميل DESC;
-- أكبر طلبية
/* , اختر رقم الطلب
اسم العميل والربح المحسوب، ثم قم بتجميع البيانات حسب
*/
-- رقم الطلب والعميل
-- ورتب النتائج حسب ربح الطلب بشكل تنازلي
SELECT
رقم_الطلب,
العميل,
SUM((سعر_البيع - التكلفة) * العدد) AS
الأرباح_حسب_العميل_و_رقم_الطلب
FROM marbles_fahad
GROUP BY رقم_الطلب, العميل
ORDER BY الأرباح_حسب_العميل_و_رقم_الطلب DESC;
اترك تعليقاً