{"id":"l-pda-2-1","courseId":"python-data-analysis","lang":"ar","kind":"lesson","summary":"ابنِ Series و DataFrame في pandas من قوائم Python وقواميسها، وأجرِ الحسابات على أعمدة كاملة دفعة واحدة، وتوقّع كيف تحاذي pandas القيم بحسب تسميات الفهرس.","html":"<p>في تمرين القسم السابق، كانت أسماء الأشهر في قائمة والإيرادات في قائمة أخرى، واضطررت إلى إيجاد أفضل شهر بموقعه ثم البحث عن اسمه في القائمة الأخرى. رتّب إحدى القائمتين وانسَ الأخرى، فيحصل كل شهر على إيراد خاطئ دون أي رسالة خطأ. وُجدت pandas لتجعل هذا النوع من الأخطاء صعبًا: القيم تحمل تسمياتها معها.</p>\n<h2 id=\"sec-1\" tabindex=\"-1\">الـ Series: عمود له تسميات</h2>\n<p>الـ <strong>Series</strong> مصفوفة أحادية البعد من القيم، ومعها <strong>فهرس (index)</strong>: تسمية لكل قيمة.</p>\n<div class=\"code-block\" dir=\"ltr\" data-lang=\"python\" data-run=\"python\" data-index=\"0\"><div class=\"code-head\"><span class=\"code-title\">Python</span><span class=\"code-actions\"><button type=\"button\" class=\"code-btn code-run\" data-action=\"run\" data-lang=\"python\" data-index=\"0\" aria-label=\"شغّل هذا المثال\"><svg class=\"icon \" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\" focusable=\"false\"><path d=\"M5 5a2 2 0 0 1 3.008-1.728l11.997 6.998a2 2 0 0 1 .003 3.458l-12 7A2 2 0 0 1 5 19z\"/></svg><span>تشغيل</span></button><button type=\"button\" class=\"code-btn\" data-action=\"copy\" aria-label=\"نسخ الكود\"><svg class=\"icon \" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\" focusable=\"false\"><rect width=\"14\" height=\"14\" x=\"8\" y=\"8\" rx=\"2\" ry=\"2\"/><path d=\"M4 16c-1.1 0-2-.9-2-2V4c0-1.1.9-2 2-2h10c1.1 0 2 .9 2 2\"/></svg><span>نسخ</span></button></span></div><pre class=\"shiki\" tabindex=\"0\"><code><span class=\"line\"><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">import</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\"> pandas </span><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">as</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\"> pd</span></span>\n<span class=\"line\"></span>\n<span class=\"line\"><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">months </span><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">=</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\"> [</span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"Jan\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"Feb\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"Mar\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"Apr\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"May\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"Jun\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">,</span></span>\n<span class=\"line\"><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">          \"Jul\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"Aug\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"Sep\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"Oct\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"Nov\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"Dec\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">]</span></span>\n<span class=\"line\"><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">revenue </span><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">=</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\"> pd.Series(</span></span>\n<span class=\"line\"><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">    [</span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">16167</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">14906</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">18208</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">18817</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">17428</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">13933</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">,</span></span>\n<span class=\"line\"><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">     22968</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">32042</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">25514</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">30339</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">75334</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">41153</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">],</span></span>\n<span class=\"line\"><span style=\"color:#953800;--shiki-dark:#FFA657\">    index</span><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">=</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">months,</span></span>\n<span class=\"line\"><span style=\"color:#953800;--shiki-dark:#FFA657\">    name</span><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">=</span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"revenue_2025\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">,</span></span>\n<span class=\"line\"><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">)</span></span>\n<span class=\"line\"><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">print</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">(revenue.head(</span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">3</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">))</span></span>\n<span class=\"line\"><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">print</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">(revenue[</span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"Nov\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">], revenue.idxmax(), revenue.sum())</span></span></code></pre><div class=\"run-output\" data-run-output=\"0\" hidden></div></div>\n<p>السطر <code dir=\"ltr\">import pandas as pd</code> يحمّل المكتبة باسمها المختصر المتعارف عليه عالميًا؛ كل درس تعليمي عن pandas وكل إجابة على Stack Overflow تستخدم <code dir=\"ltr\">pd</code>. و<code dir=\"ltr\">revenue[&quot;Nov&quot;]</code> تبحث عن قيمة بتسميتها، و<code dir=\"ltr\">idxmax()</code> تعيد <strong>تسمية</strong> أكبر قيمة، فيختصر كل ذلك العناء مع القائمتين المتوازيتين في القسم 1 في استدعاء واحد.</p>\n<p>السطر الأخير من الـ Series المطبوعة يقول <code dir=\"ltr\">Name: revenue_2025, dtype: int64</code>. الـ <strong>dtype</strong> هو نوع كل القيم في العمود: <code dir=\"ltr\">int64</code> للأعداد الصحيحة، و<code dir=\"ltr\">float64</code> للأعداد العشرية، و<code dir=\"ltr\">object</code> (أو <code dir=\"ltr\">str</code> في pandas 3) للنصوص، و<code dir=\"ltr\">bool</code>، و<code dir=\"ltr\">datetime64</code> للتواريخ. عمود واحد، نوع واحد؛ وهذه القاعدة هي ما يجعل pandas سريعة.</p>\n<h2 id=\"sec-2\" tabindex=\"-1\">الحساب على كل القيم دفعة واحدة</h2>\n<p>العمليات الحسابية والمقارنات على الـ Series تُطبَّق على كل قيمة، وتعيد Series جديدة لها الفهرس نفسه. يُسمّى هذا كودًا <strong>متّجهًا (vectorised)</strong>: تصف العملية على العمود كله، وتنفّذ pandas الحلقة بكود مُترجَم سريع.</p>\n<div class=\"code-block\" dir=\"ltr\" data-lang=\"python\" data-run=\"python\" data-index=\"1\"><div class=\"code-head\"><span class=\"code-title\">Python</span><span class=\"code-actions\"><button type=\"button\" class=\"code-btn code-run\" data-action=\"run\" data-lang=\"python\" data-index=\"1\" aria-label=\"شغّل هذا المثال\"><svg class=\"icon \" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\" focusable=\"false\"><path d=\"M5 5a2 2 0 0 1 3.008-1.728l11.997 6.998a2 2 0 0 1 .003 3.458l-12 7A2 2 0 0 1 5 19z\"/></svg><span>تشغيل</span></button><button type=\"button\" class=\"code-btn\" data-action=\"copy\" aria-label=\"نسخ الكود\"><svg class=\"icon \" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\" focusable=\"false\"><rect width=\"14\" height=\"14\" x=\"8\" y=\"8\" rx=\"2\" ry=\"2\"/><path d=\"M4 16c-1.1 0-2-.9-2-2V4c0-1.1.9-2 2-2h10c1.1 0 2 .9 2 2\"/></svg><span>نسخ</span></button></span></div><pre class=\"shiki\" tabindex=\"0\"><code><span class=\"line\"><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">import</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\"> pandas </span><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">as</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\"> pd</span></span>\n<span class=\"line\"></span>\n<span class=\"line\"><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">revenue </span><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">=</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\"> pd.Series([</span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">30339</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">75334</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">41153</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">], </span><span style=\"color:#953800;--shiki-dark:#FFA657\">index</span><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">=</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">[</span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"Oct\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"Nov\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"Dec\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">])</span></span>\n<span class=\"line\"><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">print</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">(revenue </span><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">*</span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\"> 1.05</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">)              </span><span style=\"color:#6E7781;--shiki-dark:#8B949E\"># every month, 5% higher</span></span>\n<span class=\"line\"><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">print</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">(revenue </span><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">/</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\"> revenue.sum())     </span><span style=\"color:#6E7781;--shiki-dark:#8B949E\"># each month's share of Q4</span></span>\n<span class=\"line\"><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">print</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">(revenue </span><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">></span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\"> 40000</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">)             </span><span style=\"color:#6E7781;--shiki-dark:#8B949E\"># a Series of True/False</span></span></code></pre><div class=\"run-output\" data-run-output=\"1\" hidden></div></div>\n<p>الـ Series المكوّنة من <code dir=\"ltr\">True</code>/<code dir=\"ltr\">False</code> في السطر الأخير تبدو الآن مجرّد تفصيل جانبي. في الدرس 2.4 تصبح الطريقة الأساسية لتصفية الصفوف.</p>\n<h2 id=\"sec-3\" tabindex=\"-1\">المحاذاة: pandas تطابق التسميات لا المواقع</h2>\n<p>حين تجمع بين Series وأخرى، تحاذي pandas بينهما بحسب تسمية الفهرس قبل أن تحسب. هذا الربع الرابع من 2025 مقابل الربع الرابع من 2024، والأشهر مكتوبة عمدًا بترتيب مختلف، وأحدها مفقود:</p>\n<div class=\"code-block\" dir=\"ltr\" data-lang=\"python\" data-run=\"python\" data-index=\"2\"><div class=\"code-head\"><span class=\"code-title\">Python</span><span class=\"code-actions\"><button type=\"button\" class=\"code-btn code-run\" data-action=\"run\" data-lang=\"python\" data-index=\"2\" aria-label=\"شغّل هذا المثال\"><svg class=\"icon \" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\" focusable=\"false\"><path d=\"M5 5a2 2 0 0 1 3.008-1.728l11.997 6.998a2 2 0 0 1 .003 3.458l-12 7A2 2 0 0 1 5 19z\"/></svg><span>تشغيل</span></button><button type=\"button\" class=\"code-btn\" data-action=\"copy\" aria-label=\"نسخ الكود\"><svg class=\"icon \" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\" focusable=\"false\"><rect width=\"14\" height=\"14\" x=\"8\" y=\"8\" rx=\"2\" ry=\"2\"/><path d=\"M4 16c-1.1 0-2-.9-2-2V4c0-1.1.9-2 2-2h10c1.1 0 2 .9 2 2\"/></svg><span>نسخ</span></button></span></div><pre class=\"shiki\" tabindex=\"0\"><code><span class=\"line\"><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">import</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\"> pandas </span><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">as</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\"> pd</span></span>\n<span class=\"line\"></span>\n<span class=\"line\"><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">q4_2025 </span><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">=</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\"> pd.Series([</span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">30339</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">75334</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">41153</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">], </span><span style=\"color:#953800;--shiki-dark:#FFA657\">index</span><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">=</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">[</span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"Oct\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"Nov\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"Dec\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">])</span></span>\n<span class=\"line\"><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">q4_2024 </span><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">=</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\"> pd.Series([</span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">29177</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">9360</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">], </span><span style=\"color:#953800;--shiki-dark:#FFA657\">index</span><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">=</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">[</span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"Nov\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"Oct\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">])</span></span>\n<span class=\"line\"><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">print</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">(q4_2025 </span><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">-</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\"> q4_2024)</span></span></code></pre><div class=\"run-output\" data-run-output=\"2\" hidden></div></div>\n<p>يُطرح أكتوبر من أكتوبر ونوفمبر من نوفمبر، بغضّ النظر عن الترتيب. ديسمبر موجود في 2025 فقط، فنتيجته <code dir=\"ltr\">NaN</code> (“ليس رقمًا”)، وهي علامة pandas للقيمة المفقودة. لاحظ أن النتيجة أصبحت <code dir=\"ltr\">float64</code>: في الأعمدة الكلاسيكية المبنية على NumPy، تكون <code dir=\"ltr\">NaN</code> عددًا عشريًا، فالعمود الصحيح الذي يكتسب قيمة مفقودة يتحوّل إلى أعداد عشرية.</p>\n<figure class=\"diagram\"><svg class=\"diagram-svg\" focusable=\"false\" viewBox=\"0 0 700 230\" role=\"img\" aria-labelledby=\"l-pda-2-1-t1\"><defs><marker id=\"arrow-l-pda-2-1-1\" viewBox=\"0 0 10 10\" refX=\"9\" refY=\"5\" markerWidth=\"7\" markerHeight=\"7\" orient=\"auto-start-reverse\"><path d=\"M0 0 L10 5 L0 10 z\" class=\"d-arrowhead\"/></marker></defs>\n  <title id=\"l-pda-2-1-t1\">الـ Series على اليسار فيها Oct و Nov و Dec. والـ Series على اليمين فيها Nov و Oct بترتيب مختلف. خطوط تصل بين التسميات المتطابقة. النتيجة فيها Oct و Nov محسوبين، و Dec قيمته NaN لأنه بلا نظير.</title>\n  <text class=\"d-label-strong\" x=\"70\" y=\"26\" text-anchor=\"middle\">q4_2025</text>\n  <rect class=\"d-box\" x=\"20\" y=\"40\" width=\"100\" height=\"40\" rx=\"6\"/>\n  <text class=\"d-label\" x=\"70\" y=\"65\" text-anchor=\"middle\">Oct 30339</text>\n  <rect class=\"d-box\" x=\"20\" y=\"90\" width=\"100\" height=\"40\" rx=\"6\"/>\n  <text class=\"d-label\" x=\"70\" y=\"115\" text-anchor=\"middle\">Nov 75334</text>\n  <rect class=\"d-box\" x=\"20\" y=\"140\" width=\"100\" height=\"40\" rx=\"6\"/>\n  <text class=\"d-label\" x=\"70\" y=\"165\" text-anchor=\"middle\">Dec 41153</text>\n  <text class=\"d-label-strong\" x=\"300\" y=\"26\" text-anchor=\"middle\">q4_2024</text>\n  <rect class=\"d-box\" x=\"250\" y=\"40\" width=\"100\" height=\"40\" rx=\"6\"/>\n  <text class=\"d-label\" x=\"300\" y=\"65\" text-anchor=\"middle\">Nov 29177</text>\n  <rect class=\"d-box\" x=\"250\" y=\"90\" width=\"100\" height=\"40\" rx=\"6\"/>\n  <text class=\"d-label\" x=\"300\" y=\"115\" text-anchor=\"middle\">Oct 9360</text>\n  <path class=\"d-line d-dashed\" d=\"M120 60 L250 110\"/>\n  <path class=\"d-line d-dashed\" d=\"M120 110 L250 60\"/>\n  <path class=\"d-arrow\" d=\"M370 110 L440 110\" marker-end=\"url(#arrow-l-pda-2-1-1)\"/>\n  <text class=\"d-label-strong\" x=\"560\" y=\"26\" text-anchor=\"middle\">الفرق</text>\n  <rect class=\"d-box-success\" x=\"490\" y=\"40\" width=\"140\" height=\"40\" rx=\"6\"/>\n  <text class=\"d-label\" x=\"560\" y=\"65\" text-anchor=\"middle\">Oct 20979</text>\n  <rect class=\"d-box-success\" x=\"490\" y=\"90\" width=\"140\" height=\"40\" rx=\"6\"/>\n  <text class=\"d-label\" x=\"560\" y=\"115\" text-anchor=\"middle\">Nov 46157</text>\n  <rect class=\"d-box-warn\" x=\"490\" y=\"140\" width=\"140\" height=\"40\" rx=\"6\"/>\n  <text class=\"d-label\" x=\"560\" y=\"165\" text-anchor=\"middle\">Dec NaN</text>\n  <text class=\"d-label-muted\" x=\"350\" y=\"215\" text-anchor=\"middle\">تُطابَق التسميات أولًا؛ والتسمية التي بلا نظير تعطي NaN</text>\n</svg><figcaption>تتّحد الـ Series بمطابقة تسميات الفهرس</figcaption></figure>\n<aside class=\"callout callout-mistake\" role=\"note\"><p class=\"callout-title\"><svg class=\"icon \" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\" focusable=\"false\"><path d=\"m21.73 18-8-14a2 2 0 0 0-3.48 0l-8 14A2 2 0 0 0 4 21h16a2 2 0 0 0 1.73-3\"/><path d=\"M12 9v4\"/><path d=\"M12 17h.01\"/></svg><span><span class=\"callout-kind\">خطأ شائع</span><span class=\"callout-sep\" aria-hidden=\"true\"> · </span>توقّع المطابقة بحسب الموقع</span></p>\n<p>إذا كان لـ Series وأخرى فهرسان مختلفان، كأن تكون إحداهما مسمّاة بأسماء الأشهر والأخرى بأرقامها، فكل نتيجة ستكون <code dir=\"ltr\">NaN</code> ولن يظهر أي خطأ. حين تعيد عملية حسابية فجأة عمودًا كاملًا من <code dir=\"ltr\">NaN</code>، قارن الفهرسين بـ <code dir=\"ltr\">print(a.index, b.index)</code> قبل أي شيء آخر.</p>\n</aside>\n<h2 id=\"sec-4\" tabindex=\"-1\">الـ DataFrame: جدول من الـ Series</h2>\n<p>الـ <strong>DataFrame</strong> عدة Series جنبًا إلى جنب، تتشارك فهرسًا واحدًا. أسهل طريقة لبناء DataFrame صغير هي شكل قاموس القوائم الذي تعرّفت عليه في الدرس 1.3، مفتاح لكل عمود:</p>\n<div class=\"code-block\" dir=\"ltr\" data-lang=\"python\" data-run=\"python\" data-index=\"3\"><div class=\"code-head\"><span class=\"code-title\">Python</span><span class=\"code-actions\"><button type=\"button\" class=\"code-btn code-run\" data-action=\"run\" data-lang=\"python\" data-index=\"3\" aria-label=\"شغّل هذا المثال\"><svg class=\"icon \" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\" focusable=\"false\"><path d=\"M5 5a2 2 0 0 1 3.008-1.728l11.997 6.998a2 2 0 0 1 .003 3.458l-12 7A2 2 0 0 1 5 19z\"/></svg><span>تشغيل</span></button><button type=\"button\" class=\"code-btn\" data-action=\"copy\" aria-label=\"نسخ الكود\"><svg class=\"icon \" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\" focusable=\"false\"><rect width=\"14\" height=\"14\" x=\"8\" y=\"8\" rx=\"2\" ry=\"2\"/><path d=\"M4 16c-1.1 0-2-.9-2-2V4c0-1.1.9-2 2-2h10c1.1 0 2 .9 2 2\"/></svg><span>نسخ</span></button></span></div><pre class=\"shiki\" tabindex=\"0\"><code><span class=\"line\"><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">import</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\"> pandas </span><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">as</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\"> pd</span></span>\n<span class=\"line\"></span>\n<span class=\"line\"><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">products </span><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">=</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\"> pd.DataFrame({</span></span>\n<span class=\"line\"><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">    \"name\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">: [</span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"Cast Iron Skillet 26cm\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"Burr Coffee Grinder\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"Standing Desk 140cm\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"Cork Yoga Mat\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">],</span></span>\n<span class=\"line\"><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">    \"unit_price\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">: [</span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">39</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">129</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">449</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">72</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">],</span></span>\n<span class=\"line\"><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">    \"unit_cost\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">: [</span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">17.45</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">76.99</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">204.98</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">41.52</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">],</span></span>\n<span class=\"line\"><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">})</span></span>\n<span class=\"line\"><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">print</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">(products)</span></span>\n<span class=\"line\"><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">print</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">(products.shape)       </span><span style=\"color:#6E7781;--shiki-dark:#8B949E\"># (rows, columns)</span></span>\n<span class=\"line\"><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">print</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">(products.dtypes)</span></span></code></pre><div class=\"run-output\" data-run-output=\"3\" hidden></div></div>\n<p>ثلاث خصائص (attributes) تصف أي DataFrame، وستطبعها باستمرار. <code dir=\"ltr\">shape</code> هو زوج (الصفوف، الأعمدة)، و<code dir=\"ltr\">columns</code> تسرد أسماء الأعمدة، و<code dir=\"ltr\">index</code> يحمل تسميات الصفوف. لا أقواس بعد أيٍّ منها، لأنها حقائق مخزّنة عن الجدول وليست أفعالًا؛ أما <code dir=\"ltr\">head()</code> و<code dir=\"ltr\">sum()</code> فتقومان بعمل، لذا تُستدعيان بأقواس. الخلط بين الاثنين يعطيك إما method مطبوعة بالشكل <code dir=\"ltr\">&lt;bound method ...&gt;</code> أو <code dir=\"ltr\">TypeError: 'tuple' object is not callable</code>، وكلاهما صار بإمكانك التعرّف عليه الآن.</p>\n<p>أعطت pandas الصفوف فهرسًا افتراضيًا من 0 إلى 3. كل عمود Series تستطيع استخراجها بالأقواس المربعة، والعمليات الحسابية بين الأعمدة تتحاذى صفًا بصف لأن الأعمدة تتشارك ذلك الفهرس:</p>\n<div class=\"code-block\" dir=\"ltr\" data-lang=\"python\" data-run=\"python\" data-index=\"4\"><div class=\"code-head\"><span class=\"code-title\">Python</span><span class=\"code-actions\"><button type=\"button\" class=\"code-btn code-run\" data-action=\"run\" data-lang=\"python\" data-index=\"4\" aria-label=\"شغّل هذا المثال\"><svg class=\"icon \" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\" focusable=\"false\"><path d=\"M5 5a2 2 0 0 1 3.008-1.728l11.997 6.998a2 2 0 0 1 .003 3.458l-12 7A2 2 0 0 1 5 19z\"/></svg><span>تشغيل</span></button><button type=\"button\" class=\"code-btn\" data-action=\"copy\" aria-label=\"نسخ الكود\"><svg class=\"icon \" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\" focusable=\"false\"><rect width=\"14\" height=\"14\" x=\"8\" y=\"8\" rx=\"2\" ry=\"2\"/><path d=\"M4 16c-1.1 0-2-.9-2-2V4c0-1.1.9-2 2-2h10c1.1 0 2 .9 2 2\"/></svg><span>نسخ</span></button></span></div><pre class=\"shiki\" tabindex=\"0\"><code><span class=\"line\"><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">import</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\"> pandas </span><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">as</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\"> pd</span></span>\n<span class=\"line\"></span>\n<span class=\"line\"><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">products </span><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">=</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\"> pd.DataFrame({</span></span>\n<span class=\"line\"><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">    \"name\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">: [</span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"Cast Iron Skillet 26cm\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"Burr Coffee Grinder\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"Standing Desk 140cm\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"Cork Yoga Mat\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">],</span></span>\n<span class=\"line\"><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">    \"unit_price\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">: [</span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">39</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">129</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">449</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">72</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">],</span></span>\n<span class=\"line\"><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">    \"unit_cost\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">: [</span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">17.45</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">76.99</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">204.98</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">41.52</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">],</span></span>\n<span class=\"line\"><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">})</span></span>\n<span class=\"line\"><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">margin </span><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">=</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\"> products[</span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"unit_price\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">] </span><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">-</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\"> products[</span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"unit_cost\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">]</span></span>\n<span class=\"line\"><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">print</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">(margin)</span></span>\n<span class=\"line\"><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">print</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">(</span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">type</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">(products[</span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"unit_price\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">]))</span></span></code></pre><div class=\"run-output\" data-run-output=\"4\" hidden></div></div>\n<p>تربح المقلاة 21.55 دولارًا عن كل وحدة، والمكتب الواقف 244.02. أربعة صفوف أو أربعة ملايين، الكود هو نفسه، وهذا هو الوعد الحقيقي لـ pandas: تفكّر بالأعمدة لا بالخلايا.</p>\n<aside class=\"callout callout-tip\" role=\"note\"><p class=\"callout-title\"><svg class=\"icon \" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\" focusable=\"false\"><path d=\"M15 14c.2-1 .7-1.7 1.5-2.5 1-.9 1.5-2.2 1.5-3.5A6 6 0 0 0 6 8c0 1 .2 2.2 1.5 3.5.7.7 1.3 1.5 1.5 2.5\"/><path d=\"M9 18h6\"/><path d=\"M10 22h4\"/></svg><span><span class=\"callout-kind\">نصيحة</span><span class=\"callout-sep\" aria-hidden=\"true\"> · </span>الفرق بين print(df) و df</span></p>\n<p>في Jupyter notebook، كتابة <code dir=\"ltr\">products</code> وحدها في آخر سطر من الخلية تعرض جدولًا منسّقًا. أما في الـ scripts وفي كتل Run في هذه الدورة، فلا يظهر شيء ما لم تستدعِ <code dir=\"ltr\">print()</code>. الكائن هو نفسه في الحالتين؛ الاختلاف في العرض فقط.</p>\n</aside>\n<p>بناء الجداول باليد للتعلّم فقط. في الدرس التالي تحمّل ملفات CSV الحقيقية الخاصة بـ Cartwheel، وتتعلّم روتين الفحص الذي تشغّله قبل أن تثق بأيٍّ منها.</p>\n","toc":[{"id":"sec-1","text":"الـ Series: عمود له تسميات","level":2},{"id":"sec-2","text":"الحساب على كل القيم دفعة واحدة","level":2},{"id":"sec-3","text":"المحاذاة: pandas تطابق التسميات لا المواقع","level":2},{"id":"sec-4","text":"الـ DataFrame: جدول من الـ Series","level":2}],"takeaways":["الـ Series عمود من القيم له فهرس (index) من التسميات؛ والـ DataFrame جدول من Series تتشارك فهرسًا واحدًا.","العمليات الحسابية على الـ Series تُطبَّق على كل القيم دفعة واحدة، فتكتب <code dir=\"ltr\">prices * 1.05</code> بدلًا من حلقة تكرار.","العمليات بين Series وأخرى تتحاذى بحسب تسمية الفهرس لا بحسب الموقع؛ والتسميات الموجودة في طرف واحد فقط تنتج <code dir=\"ltr\">NaN</code>.","<code dir=\"ltr\">df[&quot;col&quot;]</code> تعطيك عمودًا واحدًا على هيئة Series، و<code dir=\"ltr\">df.shape</code> و<code dir=\"ltr\">df.columns</code> و<code dir=\"ltr\">df.index</code> و<code dir=\"ltr\">df.dtypes</code> تصف الجدول."],"further":[{"title":"Intro to data structures (Series and DataFrame)","url":"https://pandas.pydata.org/docs/user_guide/dsintro.html"},{"title":"pandas.DataFrame reference","url":"https://pandas.pydata.org/docs/reference/api/pandas.DataFrame.html"}],"quiz":[{"q":"<p>ما قيمة <code dir=\"ltr\">growth[&quot;Oct&quot;]</code>؟</p>\n<div class=\"code-block\" dir=\"ltr\" data-lang=\"python\" data-index=\"0\"><div class=\"code-head\"><span class=\"code-title\">Python</span><span class=\"code-actions\"><button type=\"button\" class=\"code-btn\" data-action=\"copy\" aria-label=\"نسخ الكود\"><svg class=\"icon \" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\" focusable=\"false\"><rect width=\"14\" height=\"14\" x=\"8\" y=\"8\" rx=\"2\" ry=\"2\"/><path d=\"M4 16c-1.1 0-2-.9-2-2V4c0-1.1.9-2 2-2h10c1.1 0 2 .9 2 2\"/></svg><span>نسخ</span></button></span></div><pre class=\"shiki\" tabindex=\"0\"><code><span class=\"line\"><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">y2024 </span><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">=</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\"> pd.Series([</span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">9360</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">29177</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">], </span><span style=\"color:#953800;--shiki-dark:#FFA657\">index</span><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">=</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">[</span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"Oct\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"Nov\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">])</span></span>\n<span class=\"line\"><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">y2025 </span><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">=</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\"> pd.Series([</span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">75334</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0550AE;--shiki-dark:#79C0FF\">30339</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">], </span><span style=\"color:#953800;--shiki-dark:#FFA657\">index</span><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">=</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">[</span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"Nov\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">, </span><span style=\"color:#0A3069;--shiki-dark:#A5D6FF\">\"Oct\"</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">])</span></span>\n<span class=\"line\"><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\">growth </span><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">=</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\"> y2025 </span><span style=\"color:#CF222E;--shiki-dark:#FF7B72\">-</span><span style=\"color:#1F2328;--shiki-dark:#E6EDF3\"> y2024</span></span></code></pre></div>\n","options":[{"text":"<code dir=\"ltr\">65,974</code>، أي القيمة الأولى ناقص القيمة الأولى","why":"هذا تفكير بحسب الموقع. تطابق pandas القيم بحسب تسمياتها، لا بحسب ترتيبها."},{"text":"<code dir=\"ltr\">20,979</code>، أي أكتوبر 2025 ناقص أكتوبر 2024","why":"صحيح. تحاذي pandas الـ Series الاثنتين على الفهرس، فيُطرح كل شهر من الشهر نفسه، أيًّا كان الترتيب الذي كُتبا به."},{"text":"<code dir=\"ltr\">NaN</code>، لأن الفهرسين بترتيب مختلف","why":"الترتيب لا يهم في المحاذاة؛ وحدها التسميات التي تظهر في طرف واحد تنتج <code dir=\"ltr\">NaN</code>."}],"answer":1},{"q":"<p><code dir=\"ltr\">products</code> هو DataFrame فيه 48 صفًا و7 أعمدة. ماذا تعيد <code dir=\"ltr\">products.shape</code>؟</p>","options":[{"text":"<code dir=\"ltr\">(7, 48)</code>","why":"الشكل (shape) دائمًا الصفوف أولًا ثم الأعمدة."},{"text":"<code dir=\"ltr\">336</code>","why":"هذه قيمة <code dir=\"ltr\">products.size</code>، أي العدد الكلي للخلايا."},{"text":"<code dir=\"ltr\">(48, 7)</code>","why":"صحيح. <code dir=\"ltr\">shape</code> هو tuple من (الصفوف، الأعمدة)، وهو أسرع فحص سلامة بعد تحميل البيانات."},{"text":"<code dir=\"ltr\">48</code>","why":"هذه قيمة <code dir=\"ltr\">len(products)</code>، التي تعدّ الصفوف فقط."}],"answer":2},{"q":"<p>أيّ سطر يرفع سعر كل منتج بنسبة 5% دون حلقة تكرار؟</p>","options":[{"text":"<code dir=\"ltr\">products[&quot;unit_price&quot;] * 1.05</code>","why":"صحيح. العمليات الحسابية على الـ Series تُطبَّق على كل قيمة وتعيد Series جديدة بالطول نفسه."},{"text":"<code dir=\"ltr\">[p * 1.05 for p in products]</code>","why":"المرور على DataFrame بحلقة يعطيك أسماء أعمدته لا صفوفه، فيحاول هذا الكود ضرب نصوص."},{"text":"<code dir=\"ltr\">products * 1.05</code>","why":"هذا يضرب كل الأعمدة، ومنها الأسماء والمعرّفات، ويفشل مع الأعمدة النصية."}],"answer":0},{"q":"<p>في آخر تمرين من القسم 1 احتفظت بأسماء الأشهر والإيرادات في قائمتين متوازيتين. ما المشكلة التي تحلّها الـ Series؟</p>","options":[{"text":"القوائم لا تستطيع أن تحمل أكثر من 12 قيمة.","why":"القوائم تحمل ملايين القيم؛ الحجم لم يكن المشكلة قط."},{"text":"القوائم لا تستطيع تخزين أعداد عشرية.","why":"القوائم تحمل أي نوع، ومنها الأعداد العشرية."},{"text":"التسميات تنتقل مع القيم، فلا يمكن للترتيب أو التصفية أن يخلطا أيّ إيراد يخصّ أيّ شهر.","why":"صحيح. مع قائمتين، ترتيب إحداهما دون الأخرى يكسر الربط بينهما بصمت. أما الـ Series فتحفظ التسمية والقيمة معًا."}],"answer":2}],"exercise":{"kind":"python","files":[],"starter":"import pandas as pd\n\nmonths = [\"Jan\", \"Feb\", \"Mar\", \"Apr\", \"May\", \"Jun\",\n          \"Jul\", \"Aug\", \"Sep\", \"Oct\", \"Nov\", \"Dec\"]\nvalues = [16167, 14906, 18208, 18817, 17428, 13933,\n          22968, 32042, 25514, 30339, 75334, 41153]\n\n# 1. A Series of the values, labelled by month\nrevenue = None\n\n# 2. Label of the best month\nbest_month = None\n\n# 3. Each month's share of the year (a Series that sums to 1)\nshare = None\n\n# 4. A DataFrame with columns name, unit_price, unit_cost for these products\n#    Cast Iron Skillet 26cm  39  17.45\n#    Burr Coffee Grinder    129  76.99\n#    2-Person Dome Tent     149  83.09\nproducts = None\n\n# 5. A Series: unit_price minus unit_cost for each product\nmargin = None\n","solution":"import pandas as pd\n\nmonths = [\"Jan\", \"Feb\", \"Mar\", \"Apr\", \"May\", \"Jun\",\n          \"Jul\", \"Aug\", \"Sep\", \"Oct\", \"Nov\", \"Dec\"]\nvalues = [16167, 14906, 18208, 18817, 17428, 13933,\n          22968, 32042, 25514, 30339, 75334, 41153]\n\nrevenue = pd.Series(values, index=months)\nbest_month = revenue.idxmax()\nshare = revenue / revenue.sum()\n\nproducts = pd.DataFrame({\n    \"name\": [\"Cast Iron Skillet 26cm\", \"Burr Coffee Grinder\", \"2-Person Dome Tent\"],\n    \"unit_price\": [39, 129, 149],\n    \"unit_cost\": [17.45, 76.99, 83.09],\n})\nmargin = products[\"unit_price\"] - products[\"unit_cost\"]\n","checks":[{"id":"series","test":"isinstance(revenue, pd.Series) and list(revenue.index) == months and int(revenue['Nov']) == 75334"},{"id":"best-month","test":"best_month == 'Nov'"},{"id":"share","test":"isinstance(share, pd.Series) and round(float(share.sum()), 6) == 1.0 and round(float(share['Nov']), 4) == 0.2305"},{"id":"products","test":"isinstance(products, pd.DataFrame) and products.shape == (3, 3) and set(products.columns) == {'name', 'unit_price', 'unit_cost'}"},{"id":"margin","test":"isinstance(margin, pd.Series) and [round(float(x), 2) for x in margin] == [21.55, 52.01, 65.91]"}],"title":"أول Series وأول DataFrame لك","prompt":"<p>ابنِ <code dir=\"ltr\">revenue</code>، وهي Series من <code dir=\"ltr\">values</code> مسمّاة بـ <code dir=\"ltr\">months</code>. اجعل <code dir=\"ltr\">best_month</code> تسمية أكبر قيمة فيها، و<code dir=\"ltr\">share</code> حصة كل شهر من مجموع السنة (Series مجموعها 1). ثم ابنِ <code dir=\"ltr\">products</code>، وهو DataFrame له الأعمدة <code dir=\"ltr\">name</code> و<code dir=\"ltr\">unit_price</code> و<code dir=\"ltr\">unit_cost</code> ويحتوي المنتجات الثلاثة المذكورة في التعليقات، بهذا الترتيب، و<code dir=\"ltr\">margin</code>، وهي Series تساوي <code dir=\"ltr\">unit_price</code> ناقص <code dir=\"ltr\">unit_cost</code>.</p>\n","hints":["<code dir=\"ltr\">pd.Series(values, index=months)</code> تربط التسميات بالقيم.","<code dir=\"ltr\">revenue.idxmax()</code> تعيد تسمية؛ وقسمة Series على رقم واحد تقسم كل قيمة فيها.","ابنِ الـ DataFrame من قاموس قوائم، مفتاح لكل عمود، ثم اطرح عمودًا من الآخر: <code dir=\"ltr\">products[&quot;unit_price&quot;] - products[&quot;unit_cost&quot;]</code>."],"explanation":"<p>تمرير <code dir=\"ltr\">index=months</code> يجعل كل إيراد يحمل شهره، فتجيب <code dir=\"ltr\">idxmax()</code> عن سؤال “أيّ شهر؟” مباشرة. و<code dir=\"ltr\">revenue / revenue.sum()</code> تقسم كل قيمة على مجموع واحد: الرقم المفرد يتّحد مع كل عنصر في الـ Series (ويُسمّى هذا broadcasting). أما في الـ DataFrame، فتصبح مفاتيح القاموس أسماء الأعمدة، وكل قائمة تصبح عمودًا. وطرح عمودين يحاذي بينهما بحسب فهرس الصفوف المشترك، فيكون هامش المقلاة 21.55، والمطحنة 52.01، والخيمة 65.91.</p>\n","checkLabels":{"series":"<code dir=\"ltr\">revenue</code> هي Series مسمّاة من Jan إلى Dec","best-month":"<code dir=\"ltr\">best_month</code> يساوي <code dir=\"ltr\">&quot;Nov&quot;</code>","share":"مجموع <code dir=\"ltr\">share</code> يساوي 1، ونوفمبر نحو 23%","products":"<code dir=\"ltr\">products</code> هو DataFrame بحجم 3 × 3 وبالأعمدة الصحيحة","margin":"<code dir=\"ltr\">margin</code> تحتوي 21.55 و52.01 و65.91"}},"words":614,"readMinutes":4}