مكتبة Pandas – الخطوة الثانية في علم البيانات بلغة البايثون – الجزء الأول

1 8٬800

أهلاً بكم في ثاني مقالات سلسلة مكتبات علم البيانات بـ لغة البايثون. قدمنا لكم في المقال السابق تعريفًا بسيطًا بمكتبة Numpy وكيفية تثبيتها والتعامل معها، وفي هذا المقال نتكلم عن مكتبة Pandas . الهدف الأساسي لمكتبة Pandas هو إجراء ما يسمى بـ Data Munging، والمقصود به هو إجراء تغييرات على بيانات أساسية غير مرتبة Raw data بحيث ينتج عن هذا التغيير تحويل البيانات الى شكل أخر يُمكن فهمه والتعامل معه.

هذا الموضوع يتكون من مقالين، في المقال الأول سنتعرف على:

  • كيفية تعريف إطار بيانات في مكتبة Pandas.
  • كيفية تحديد مؤشر أو عمود من إطار البيانات.
  • كيفية إضافة مؤشر، صف أو عمود إلى إطار البيانات.
  • حذف فهرس، صف أو عمود من إطار البيانات.
  • كيفية إعادة تسمية الأعمدة والفهارس في إطار البيانات.
  • كيفية عمل Format للبيانات في إطار البيانات.

وفي المقال الثاني سنتحدث عن:

  • إنشاء إطار بيانات فارغ.
  • معرفة متى، وكيف، ولماذا نقوم بإعادة تغيير شكل إطار البيانات.
  • كيفية المرور على البيانات وقراءتها في إطار البيانات.
  • كيفية تصدير إطار البيانات إلى الملف خارجي.

ما هو إطار البيانات في مكتبة Pandas ؟

يُمكننا تعريف إطار البيانات بأنه عبارة عن شكل من أشكال الجداول في قاعدة البيانات، ويتكون من أعمدة وصفوف، تُمثل الأعمدة خصائص معينة وتُمثل الصفوف القيم التي تأخذها هذه الأعمدة.

يتكون إطار البيانات في مكتبة Pandas من 3 عناصر رئيسية:

  • البيانات (data).
  • المؤشر أو الفهرس (index).
  • العمود (column).

اطار البيانات في مكتبة Pandas

كيفية بناء إطار البيانات في مكتبة Pandas

يُعتبر بناء إطار البيانات الخطوة الأولى عند البدء في إجراء عملية Data Munging باستخدام لغة البايثون. يُمكن بناء إطار البيانات فارغ دون بيانات، ويُمكن بناؤه  باستخدام تراكيب أخرى مثل Series أو مصفوفة Numpy أو حتى من خلال إطار بيانات اخر.

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

في البداية نستورد المكتبات اللازمة للعمل وهي مكتبتي Numpy و Pandas بالطريقة التالية:

import numpy as np
import pandas as pd

لنفترض أنه يوجد لدينا مصفوفة Numpy بالشكل التالي:

np_arr = np.array([[' ','Col1','Col2'],['Row1',1,2],['Row2',3,4]  ])

لبناء اطار بيانات من المصفوفة السابقة نستخدم الطريقة التالية:

df =pd.DataFrame(data=np_arr[1:,1:], index =  np_arr[1:,0],columns=np_arr[0,1:])

لاحظ كيفية إستخدام المصفوفة np_arr في بناء إطار البيانات، حيث أنه في البداية نقوم بتحديد البيانات في np_arr بإستخدام عملية Indexing ومن ثم نحدد المؤشر الخاص بإطار البيانات، ثم نُحدد أسماء الأعمدة للإطار.

لمعرفة كيفية إجراء عمليات subseting على مصفوفات Numpy يُمكن مراجعة مقال مكتبة Numpy

بناء اطار بيانات من تراكيب مختلفة

القاموس (dictionary)

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

1

إطار بيانات اخر

 

my_df = pd.DataFrame(data=[4,5,6,7], index=range(0,4), columns=['A'])
pd.DataFrame(my_df)

2.png

Series

 

my_series = pd.Series({"United Kingdom":"London", "India":"New Delhi", "United States":"Washington", "Belgium":"Brussels"})

pd.DataFrame(my_series)

3.png

بعد إنشاء إطار البيانات، يُمكن الاستعلام عن بعض التفاصيل الخاصة بإطار البيانات وذلك باستخدام بعض الخصائص والدوال التابعة لإطار البيانات.

فمثلًا، يُمكن معرفة شكل إطار البيانات (أبعاده) باستخدام الدالة shape، كما يُمكن معرفة ارتفاع إطار البيانات (عدد صفوفه) بتمرير الخاصية index للدالة len كما في المثال التالي:

 

df = pd.DataFrame(np.array([[1, 2, 3], [4, 5, 6]]))

print(df.shape)
print(len(df.index))

يُمكن استخدام df[0].count لمعرفة ارتفاع اطار البيانات، ولكن هذه الطريقة تستثني عد القيم الفارغة (NaN) اذا وجدت، لذلك فإن استخدام هذه الطريقة لها هدفها الخاص. بعد أن أنشأنا إطار البيانات ووضعنا بداخله  بيانات، حان الوقت للعمل الحقيقي.

من خلال العناوين القادمة، سوف نخطو الخطوات الأولى في التعامل مع إطار البيانات، حيث سنُغطي العمليات الأساسية التي يُمكن اجراؤها على إطار البيانات مثل الإضافة، تحديد (select)، الحذف، إعادة التسمية وغيرها. وبعد ذلك سوف نستخدم هذه العمليات للذهاب قُدماً لمواضيع أكثر تقدما في التعامل مع إطار البيانات.

 كيفية تحديد مؤشر أو عمود في اطار البيانات

قبل أن تتعلم كيفية إضافة، حذف أو إعادة تسمية مكونات إطار البيانات لديك, لابد أن تتعلم كيفية تحديد هذه المكونات واختيارها بطريقة صحيحة.

لنفترض وجود إطار باسم df ويحتوي على بيانات بالشكل التالي:

4.png

اذا أردنا الوصول للبيانات موجودة في المؤشر رقم 0 والعمود المُسمى A يُمكننا استخدام أحد الخيارات الأربع التالية:

 

print(df.iloc[0][0])

print(df.loc[0]['A'])

print(df.at[0,'A'])

print(df.iat[0,0])

print(df.get_value(0, 'A'))

كيفية إضافة مؤشر، صف أو عمود إلى إطار البيانات

عندما نبني إطار البيانات، يوجد لدينا خيار نستطيع من خلاله تحديد قيم المؤشر الذي يُحدد الصفوف، وذلك من خلال تمرير قيم المؤشر كمصفوفة للمُعطى المُسمى index. في حالة عدم تحديد قيم للمؤشر، فإن قيم المؤشر ستأخذ قيمًا تلقائية تبدأ من 0 وتزداد بقيمة 1 لكل صف.

يُمكننا تغيير المؤشر الخاص بإطار البيانات لتكون قيمه مأخوذة من عمود آخر في نفس اطار البيانات، وذلك باستخدام الدالة set_index بالطريقة التالية:

df.set_index('C')

إضافة صفوف لإطار البيانات

قبل البدء بالحديث عن موضوع الإضافة على اطار البيانات، لابد من شرح طريقة التأشير loc وكيف أنها تختلف عن طرق التأشير الأخرى مثل iloc و ix.

يعمل loc على إسم (label) المؤشر، مما يعني أنه لو مررت الرقم 2 للدالة loc فإنها سوف تبحث في اطار البيانات عن القيم التي لها اسم مؤشر بقيمة 2.

بينما iloc يعمل على موقع المؤشر، فلو مررت الرقم 2 للدالة iloc فإن النتيجة ستشمل القيم الموجودة في موقع المؤشر رقم 2.

طريقة التأشير باستخدام ix تُعتبر أكثر تعقيدا، حيث عندما يكون المؤشر من نوع رقم، فإن ix تعمل مثل loc أما إذا لم يكن المؤشر رقماً، فإن ix ستعمل عمل iloc.

قد يكون ما ذكرناه معقدا أو غامضا نوعًا ما، لذلك بالمثال يتضح المقال.

لنفترض وجود اطار بيانات df (نوع المؤشر ليس برقم) بالشكل التالي:

df = pd.DataFrame(data=np.array([[1, 2, 3], [4, 5, 6], [7, 8, 9]]), index= [2, 'A', 4], columns=[48, 49, 50])

ستكون نتيجة تمرير 2 للدالة loc ستكون كالتالي:

>> df.loc[2]

48   1

49   2

50   3

Name: 2, dtype: int32

وللدوال iloc و ix كالتالي:

>> df.iloc[2]

48   7

49   8

50   9

Name: 4, dtype: int32

>> df.ix[2]

48   7

49   8

50   9

Name: 4, dtype: int32

بعد أن شرحنا الطرق الخاصة بالتأشير، تُصبح إضافة الصفوف لإطار البيانات أمر سهلاً.

ملاحظة/ يُنصح باستخدام طريقة التأشير loc في الإضافة.

لإضافة صف بيانات لإطار البيانات بمؤشر جديد قيمته 5 ننفذ السطر التالي:

df.loc[5] = [11, 12, 13]

ويصبح إطار البيانات بالشكل التالي:

5.png

لتعديل قيم الصف الأول في إطار البيانات السابق، نستخدم نفس الطريقة ولكن بقيمة المؤشر الذي يؤشر على الصف الأول:

df.loc[2] = [10, 10, 10]

ويصبح إطار البيانات بالشكل التالي:

6.png

إضافة أعمدة لإطار البيانات

لإضافة عمود جديد باسم ‘A’ لإطار البيانات df بالقيم [10,20,30,40] ننفذ السطر التالي:

df['A'] = [10,20,30,40]

ويصبح إطار البيانات بالشكل التالي:

7.png

إعادة تهيئة مؤشر إطار البيانات

عندما يكون مؤشر إطار البيانات ليس كما نريد، نستطيع باستخدام الدالة reset_index إعادة تهيئة المؤشر.

لإعادة تهيئة المؤشر لإطار البيانات df نُنفذ السطر التالي:

df.reset_index(level=0, drop=True)

ويصبح إطار البيانات بالشكل التالي:

8.png

لاحظ أننا فقدنا قيم المؤشر السابقة، لذلك، وفي حالة أردنا أن نُبقي على قيم المؤشر السابق موجودة، بحيث يتم إضافتها كعمود جديد، نقوم باستبدال المعامل drop بالمعامل inplace:

df.reset_index(level=0, inplace=True)

ويصبح شكل الإطار كالتالي:

9.png

حذف فهرس، صف أو عمود من إطار البيانات في مكتبة Pandas

تعرفنا الى الان الى كيفية الوصول للبيانات في إطار البيانات، وتعلمنا أيضا كيفية إضافة بيانات جديدة. سنتحدث فيما يلي عن كيفية تنفيذ عمليات حذف على اطار البيانات.

حذف المؤشر

يُمكننا إتباع أربعة خيارات لحذف المؤشر من إطار البيانات.

الأول هو أن نُعيد تهيئة المؤشر كما ذكرنا سابقا.

الثاني هو أن نحذف اسم المؤشر باستخدام الأمر del df.index.name.

الثالث أن نحذف تكرار قيم المؤشر وذلك يشمل إعادة تهيئة المؤشر، ثم حذف التكرار كما في المثال التالي:

df = pd.DataFrame(data=np.array([[1, 2, 3], [4, 5, 6], [7, 8, 9], [40, 50, 60], [23, 35, 37]]),index= [2.5, 12.6, 4.8, 4.8, 2.5],columns=[48, 49, 50])                 

df.reset_index().drop_duplicates(subset='index',keep='last').set_index('index')

الرابع حذف المؤشر والصف المقابل له باستخدام الأمر التالي:

df.drop(df.index[1])

حذف عمود من إطار البيانات

لحذف عمود من إطار البيانات نستخدم الدالة drop ونمرر لها اسم العمود الذي نريد حذفه، ثم نحدد نوع الحذف بأنه حذف عمود وذلك بتمرير قيمة 1 للمعامل axis ومن ثم نُحدد إذا أردنا أن نٌجري التغيير على الإطار بشكل مباشر أم لا:

df.drop('A', axis=1, inplace=True)

يُمكن حذف العمود باستخدام الموقع بالطريقة التالية:

df.drop(df.columns[[1]], axis=1)

حذف صف من إطار البيانات

يُمكن استخدام طريقة حذف المؤشر مع الصف لحذف صف من إطار البيانات والتي ذكرناها سابقا.

في حالة وجود صفوف مكررة في اطار البيانات، يُمكن استخدام الدالة drop_duplicates  لحذف الصفوف المكررة بغض النظر عن قيمة المؤشر.

df.drop_duplicates()

كما أن من الممكن حذف الصفوف بناءً على تكرار قيم في عمود معين. لنفترض وجود إطار بيانات df بالشكل التالي:

10.png

لاحظ وجود القيمة 2 مكررة للعمود باسم 49، تستطيع حذف الصفوف التي تحتوي على هذه القيمة باستخدام الامر التالي:

df.drop_duplicates([49], keep='last')

كيفية إعادة تسمية الأعمدة والفهارس في إطار البيانات في مكتبة Pandas

لإعطاء المؤشر أو العمود في إطار البيانات اسم مختلف، يُمكن استخدام الدالة rename لهذا الغرض:

newcols = {

    48: 'new_column_1',

    49: 'new_column_2',

    50: 'new_column_3'

}

df.rename(columns=newcols, inplace=True)

وسيكون شكل إطار البيانات كالتالي:

11.png

ولإجراء التغيير على اسم المؤشر نستبدل columns بـ index كالتالي:

df.rename(index={2.5: 'a'})

وسيكون شكل إطار البيانات كالتالي:

12.png

من خلال ما سبق، تم الإجابة عن الأسئلة الأساسية لاستخدام مكتبة Pandas واطار البيانات فيها، وقد حان الوقت للذهاب أبعد من ذلك كي نُجهز أنفسنا للاستخدام الواقعي والحقيقي لهذه المكتبة، لأنه ببساطة ما تكلمنا عنه جزء بسيط مما تبقى.

كيفية عمل Format للبيانات في إطار البيانات في مكتبة Pandas

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

سنتكلم فيما يلي عن بعض الأمثلة التي تشرح كيفية تغيير البيانات داخل إطار البيانات.

استبدال النصوص في إطار البيانات

لاستبدال نصوص محددة في إطار البيانات، يُمكن ببساطة استخدام الدالة replace، بحيث نُمرر القيم التي نريد تغييرها ثم القيم الجديدة.

لنفترض وجود اطار بيانات df بالشكل التالي:

13.png

وأردنا أن نستبدل الكلمات ‘Awful’, ‘Poor’, ‘OK’, ‘Acceptable’, ‘Perfect’ بقيم رقمية 0,1,2,3,4 على الترتيب، نقوم بتنفيذ السطر التالي:

df.replace(['Awful', 'Poor', 'OK', 'Acceptable', 'Perfect'], [0, 1, 2, 3, 4])

وسيكون شكل الإطار كالتالي:

14.png

إزالة أجزاء من النصوص في إطار البيانات

تُعتبر هذه العملية روتينية ومتكررة في مهام العمل الحقيقية عند التعامل مع البيانات باستخدام مكتبة Pandas، ويتم تنفيذ عملية التغيير بشكل مباشر على القيم الموجودة في إطار البيانات.

لنفترض وجود اطار بيانات df بالشكل التالي:

15.png

لو أردنا أن نُزيل إشارة + و – من عمود result بالإضافة لإزالة الأحرف منه، نُنفذ السطر التالي:

df['result']=df['result'].map(lambda x: x.lstrip('+-').rstrip('aAbBcC'))

في الأمر السابق، استخدمنا الدالة map على العمود result لتطبيق دالة lambda على كل عناصر العمود، بحيث تأخذ الدالة كل عنصر وتقوم بإزالة الإشارات + و – من على شمال العنصر، وتزيل أي حرف من على يمنيه.

تطبيق دالة على إطار البيانات أو جزء منه

عند التعامل مع إطار البيانات الذي يحتوي أرقامًا، فغالبًا ما سنحتاج لتطبيق دالة على البيانات الموجودة فيه أو جزء منها، فمثلا، لو افترضنا إطار البيانات df يحتوي على أرقام وأردنا مضاعفة هذه القيم، نُنفذ السطر التالي:

df.apply(lambda x: x*2)

في السطر السابق، سيتم المرور على كافة القيم في إطار البيانات وإجراء عملية ضربها بالقيمة 2.

من الممكن أن نقوم بإجراء هذه العملية على عمود واحد:

df['A'].apply(lambda x: x*2)

يُمكننا تكرار نفس الأمر على صف، فمثلا، لإجراء عملية الضرب على الصف الأول:

df.loc[0].apply(lambda x: x*2)

إلى هنا انتهى الجزء الأول من هذا الموضوع.

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

 

 

1 Comment
  1. […] مكتبة Pandas – الخطوة الثانية في علم البيانات بلغة البايث… […]

اترك ردًا

Your email address will not be published.