كيفية التعامل مع التاريخ والوقت في بايثون

يعد التعامل مع بيانات التاريخ والوقت في بايثون مهارة مهمة. ستوضح هذه المقالة أهم وحدات التاريخ والوقت في بايثون.

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

هناك عدد قليل من وحدات بايثون المفيدة التي توفر وظائف تجعل التعامل مع التواريخ والأوقات أسهل. في هذه المقالة، سنقدم (مع الأمثلة) بعضًا من أكثر الأدوات فائدة للتعامل مع التواريخ والأوقات.

وحدة time

الوحدة الأولى تسمى time وتأتي مع التثبيت القياسي لـبايثون. لنبدأ بالحصول على الوقت الحالي:

>>> import time
>>> time_now = time.time()
>>> print(time_now)
... 1653035191.6578639

جرب هذا بنفسك. سيتغير الناتج الذي تحصل عليه وفقًا لوقت تنفيذ هذا الأمر. ومع ذلك، يعيد هذا الأمر رقمًا كبيرًا جدًا. هذا هو الوقت (بالثواني) الذي انقضى منذ وقت مرجعي، أو “حقبة”. بالنسبة لمعظم الأنظمة، تكون الحقبة هي الخميس 1 يناير 1970 في الساعة 00:00:00 بالتوقيت العالمي المنسق. يتم التعبير عن التواريخ والأوقات قبل هذه الحقبة برقم سلبي. إن عرض الوقت بالثواني منذ عام 1970 ليس مفيدًا بشكل خاص، لذلك يمكن عرضه كسلسلة مُنسَّقة مسبقًا:

>>> print(time.ctime(time_now))
... Fri May 20 10:26:31 2022

هنا، استخدمنا التابع ctime() لتحويل الثواني المنقضية إلى تنسيق أكثر شيوعًا.

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

>>> t1 = time.time()
>>> for i in range(4):
...     print(i)
...     time.sleep(1)
>>> t2 = time.time()
>>> print('Runtime: %s seconds'%(t2 - t1))
0
1
2
3
Runtime: 4.030589818954468 seconds

هنا نقوم بتوقيت حلقة for بأكملها. في الحلقة، نقوم ببساطة بطباعة الفهرس ثم نتوقف لمدة ثانية واحدة. راجع هذه المقالة للحصول على مزيد من المعلومات حول دالة print() سيعتمد وقت التشغيل النهائي على النظام ولكن يجب أن يكون أكثر من 4 ثوانٍ بقليل. تحتوي هذه الوحدة على دوال أكثر بكثير مما يمكننا عرضه هنا، لذا راجع الوثائق لمزيد من التفاصيل.

وحدة calendar

توفر وحدة calendar دوال تتعلق بإخراج التقويمات. كما تأتي مع التثبيت القياسي لـبايثون.

تطبع دالة calendar() التقويم للعام بأكمله. ما عليك سوى إدخال السنة، كعدد صحيح، والناتج عبارة عن سلسلة بها مسافات وأحرف سطر جديد لعرض التقويم بشكل جيد. وعلى نحو مماثل، تخرج دالة month() التقويم لهذا الشهر.

إذا اختبرت هذه الدوال، فستلاحظ أن التقويمات تستخدم يوم الإثنين كأول يوم في الأسبوع، والذي يكون مؤشره 0. يمكنك الحصول على رقم يوم الأسبوع، من 0 إلى 6، لأي تاريخ باستخدام دالة weekday(). يتم استخدام هذا المعيار لبدء الأسبوع من يوم الإثنين، عند المؤشر 0، أيضًا في وحدات بايثون الأخرى.

تتضمن فئة Calendar بعض التكرارات التي يمكنك استخدامها للتكرار خلال أيام الأسبوع وأشهر السنة. هناك أيضًا فئة TextCalendar وفئة HTMLCalendar، والتي يمكنها إنشاء تقويمات نصية عادية وHTML. مرة أخرى، راجع الوثائق للحصول على مزيد من التفاصيل حول هذه الوحدة.

وحدة datetime

بمساعدة وحدة datetime، يمكنك تعريف التواريخ والأوقات ككائنات. وكما هو مذكور في الوثائق، فإن التركيز في هذه الوحدة هو على استخراج السمات بكفاءة لعرض كائنات datetime والتلاعب بها. ولكن الأمر لا يقتصر على هذا؛ بل يمكنك أيضًا استخدامها لحساب عدد الأيام بين تاريخين. لتحديد كائن datetime، استورد الوحدة وقم بما يلي:

>>> import datetime
>>> date1 = datetime.datetime(2022, 1, 1, 12, 30, 0)

تحدد الوسائط التاريخ من السنة وحتى الميكروثانية، حيث تكون year وmonth وday وسائط مطلوبة. يمكنك أيضًا تضمين معلومات المنطقة الزمنية بشكل اختياري عند تعريف كائن datetime. إذا حاولت تعريف تاريخ غير صالح، على سبيل المثال باستخدام الوسيطة day = 35، فستحصل على ValueError: day is out of range for month.

يحتوي كائن datetime على العديد من التوابع المرتبطة به. يمكنك استرداد السنة باستخدام date1.year، الذي يعيد عددًا صحيحًا. يعمل هذا أيضًا مع معلومات التاريخ والوقت الأخرى حتى الميكروثانية. كما ناقشنا سابقًا، يمكن استرداد يوم الأسبوع (كعدد صحيح بين 0 و6) باستخدام دالة weekday():

>>> print(date1.weekday())
... 5

يتوافق العدد الصحيح 5 مع يوم السبت. يمكنك التأكد من ذلك عن طريق طباعة التقويم باستخدام وحدة calendar. جرب ذلك بنفسك.

دعنا ننشئ كائن datetime آخر:

>>> date2 = datetime.datetime(2021, 7, 31)

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

>>> time_diff = date1 - date2
>>> print('Number of days between %s and %s = %s'%(date1, date2, time_diff.days))
 
Number of days between 2022-01-01 12:30:00 and 2021-07-31 00:00:00 = 154

يؤدي هذا إلى إنشاء كائن timedelta جديد، والذي يمثل مدة زمنية. لقد استخدمنا التابع days() للحصول على فارق الوقت بالأيام، ثم قمنا بطباعة الإجابة. حتى إذا امتد فارق الوقت لعدة سنوات، فإن الدقة الأكثر لكائن timedelta ستكون بالأيام.

في المثال أعلاه، قمنا ببساطة بعرض الكائن باستخدام دالة print(). التنسيق الافتراضي عند طباعة الكائن بهذه الطريقة هو YYYY-MM-DD HH:MM:SS. تأتي وحدة datetime مع بعض الدوال المفيدة للمساعدة في تنسيق الكائنات وعرضها. على سبيل المثال، strftime() هو تابع مثيل تسمح لك بإنشاء تمثيل سلسلة لكائن datetime. فيما يلي بعض الأمثلة حول كيفية استخدام سلاسل تنسيق مختلفة لطباعة معلومات التاريخ والوقت باستخدام هذه التابع:

>>> print(date1.strftime('%Y %m %d'))
... 2022 01 01
 
>>> print(date1.strftime('%Y-%m-%d'))
... 2022-01-01
 
>>> print(date1.strftime('%A %d %B %Y'))
... Saturday 01 January 2022
 
>>> print(date1.strftime('%a %d %b %y, %H:%M:%S %p'))
... Sat 01 Jan 22, 12:30:00 PM

هناك العديد من الخيارات الأخرى لتنسيق سلسلة إخراج التاريخ/الوقت. ألق نظرة على أكواد التنسيق للحصول على بعض الإلهام.

العمل في مناطق زمنية مختلفة

الميزة الأخيرة التي سنوضحها هي كيفية التعامل مع المناطق الزمنية. عند إنشاء كائن datetime، يمكنك تحديد المنطقة الزمنية بمساعدة مكتبة pytz. للحصول على قائمة كاملة بالمناطق الزمنية، ما عليك سوى تنفيذ pytz.common_timezones في الطرفية، والتي ستطبع قائمة من السلاسل. يمكننا اختيار عدد قليل من المناطق الزمنية والتحقق من الوقت الحالي:

>>> import pytz
>>> time_zones = ['America/New_York', 'Asia/Seoul', 'Australia/Melbourne', 'Europe/Zagreb']
>>> for time_zone in time_zones:
...     print(datetime.datetime.now(tz=pytz.timezone(time_zone)))
2022-05-20 04:26:34.134504-04:00
2022-05-20 17:26:34.134504+09:00
2022-05-20 18:26:34.134504+10:00
2022-05-20 10:26:34.134504+02:00

أصبحت كائنات datetime هذه الآن “مدركة” ولا يمكنها اللعب بشكل جيد إلا مع كائنات أخرى مدركة للمنطقة الزمنية. حاول حساب فارق الوقت بين كائن مدرك وكائن عادي وستحصل على TypeError.


اكتشاف المزيد من بايثون العربي

اشترك للحصول على أحدث التدوينات المرسلة إلى بريدك الإلكتروني.

اترك تعليقاً

لن يتم نشر عنوان بريدك الإلكتروني. الحقول الإلزامية مشار إليها بـ *

Scroll to Top

اكتشاف المزيد من بايثون العربي

اشترك الآن للاستمرار في القراءة والحصول على حق الوصول إلى الأرشيف الكامل.

Continue reading