תאריכים ב-PHP

‏ • 3 באפריל, 2004

במאמר זה נסביר את אופן השימוש בפונקציות הזמנים והתאריכים ב php, וכיצד ניתן לבצע בעזרתן את המניפולציות השונות על התאריכים.


הקדמה – ייצוג הזמנים ב php

ב php, רוב העבודה עם תאריכים, מבוססת על ה timestamp ("חותמת זמן" בתירגום חופשי), אותו timestamp הוא למעשה מספר שלם ארוך המייצג את מספר השניות שעברו מאז תחילת תקופת Unix (00:00:00 GMT 01/01/1970). תקופת הזמן המינימלית – מקסימלית שתיוצג ע"י אותו timestamp היא 1901 – 2038 מכיוון שמס' שלם ארוך מיוצג בעזרת 32 סיביות, ומחישוב מהיר עולה, כי 42949672962^32 = (שתי אפשרויות בינאריות 0 או 1 בחזקת 32 סיביות), כלאמר 4294967296 כמות המס' המקסימלית שתיוצג במס' שלם ארוך, אם נחלק את הכמות הזאת למס' חיוביים ושלילים, הרי שטווח המס' שיוכל להתקיים הוא 2147483648- עד 2147483647 כלאמר, שהמס' השליליים ייצגו את מס' השניות לפני תקופת ה Unix והחיוביים את מס' השניות לאחריה מה שאומר שבשביל לקבל את כמות השנים שתיוצג לפני ואחרי תקופת היוניקס, יש להפוך את מס' השניות לשנים ע"י חישוב פשוט של 2147483648 ב 31536000 (כאשר 31536000 הוא מס' השניות בשנה) תוצאת החישוב לערך 68.02, כלאמר שהזמן שייוצג הוא .0268 שנה לפני 1970 כלאמר מתישהו ב 1901 ו 68.02 שנה אחרי 1970, זאת אומרת, מתישהו ב 2038.

הערה: מי שלא הבין את כל החישובים למיניהם, שלא יתייאש, מפני שלא תזדקקו להם, הם להמחשה בלבד, להבנה מעמיקה יותר של ייצוג ה timestamp.

אבל אם בכל זאת נרצה לדייק, טווח התאריכים המדוייק שייוצג בעזרת timestamp הוא יום שישי ה 13 בדצמבר 1901 שעה 20:45:54 עד יום שלישי ה 19 בינואר 2038 03:14:04.

הערה: כל פונקציה המבוססת על timestamp שתקבל תאריך מעבר לטווח תיצור שגיאה.

כאשר מריצים את אפליקצית ה php על Windows ולא על Linux / Unix חשוב מאוד לציין, כי מערכת ההפעלה Windows, אינה תומכת בייצוג המס' השליליים ב timestamp, לכן טווח המס' יהיה בין 0 ל 2147483647, מה שאומר, שטווח התאריכים שייוצג בעזרתו יהיה בין ה 01/01/1970 00:00:00 ל 19/01/2038 03:14:04.


הפונקציה: time












1  








time()


מחזירה את הזמן הנוכחי מיוצג במס' השניות מתחילת תקופת היוניקס

הפונקציה date












1  








date(string format [,int timestamp])


format – סוג נתון: מחרוזת
ערך: פורמט התאריך (הצורה בה הוא יוצג)

timpstamp – אופציונאלי סוג נתון: מספר שלם
ערך: הפרמטר מקבל מס' שלם שמייצג את מס' השניות שעברו מתחילת תקופת היוניקס
אם לא ניתן ערך לפרמטר, ברירת המחדל תהיה ה timestamp של הזמן הנוכחי.

ישנה רשימה של אותיות אנגליות אשר כל אחת מהן מסמלת דרך תצוגה שונה של אלמנט שונה בתאריך. לדוגמא:










1  








date("D m Y H:i:s")




  • D – שלושה אותיות המייצגות היום בשבוע ( mon, sun וכו') , m – מס' החודש בשנה,
  • Y – מס' השנה, 4 ספרות (1983 וכו'), H – השעה בפורמט 0 – 24, i – הדקות בשעה,
  • s – שניות (את רשימת האותיות המלאה ניתן למצוא במדריך הPHP שבאתר).
הפונקציה הנ"ל, תחזיר תוצאה דומה לזו: Tue 17 2004 21:55:08

ניתן לפרמט את אותו תאריך כך:










1  








 date("today is the dS")


כל אות בעלת משמעות בתצוגה,
יש "להבריח" בעזרת תו הבריחה "" ( BackSlash) בכדי למנוע את הצגתה כאלמנט של תאריך.
d – מס' היום בחודש (01 – 31), S – סיומת אנגלית למס' סידוריים (st, rd, nd, th)
הפונקציה בפורמט הזה באותו תאריך תחזיר את הערך הבא: today is the 17th


הפונקציה checkdate












1  








checkdate(int month, int day, int year)


הפונקציה מקבלת את מס' החודש, מס' היום בחודש, ואת השנה, ובודקת האם התאריך תקין, אם כן היא תחזיר true אחרת, תחזיר false
לדוגמא:










1  








checkdate(2, 23, 1987)


תחזיר אמת, מפני שאין כל פגם בתאריך ה 23/2/1987
לעומת זאת,










1  








checkdate(2, 29, 1995)


תחזיר שקר, מפני שבפברואר 1995 לא קיים ה29 לחודש, מפני שהחודש נגמר ב 28, לכן התאריך אינו תקין.

הפונקציה mktime












1  








 mktime([int hour] [,int minute] [,int second] [,int month] [,int day] [,int year] [, int isdst])


הפונקציה מקבלת אלמנטים של תאריך (שעה דקה שנייה חודש יום ושנה), ומחזירה את ה timestamp של אותו תאריך, כלאמר מס' השניות שעברו מ 01/01/1970 00:00:00 עד התאריך שצויין.
הפונקציה יכולה לקבל תאריך בין השנים 1901 – 2038 (התאריך המדוייק הוזכר בהקדמה) אם מריצים php על מערכת Windows, השנים שתקבל הפונקציה יהיו בין 1970 ל 2038 מכיוון ש Windows אינו תומך ב timestamp שלילי (שלילי = תאריכים שלפני 01/01/1970 00:00:00 )

כל הפרמטרים אופציונאלים, מה שאומר, שניתן לוותר על ציונם של פרמטרים משמאל לימין.
כלאמר, ניתן לכתוב את הפנוקציה כך mktime(hour, minute, second), מבלי לציין את שאר הפרמטרים. כל פרמטר שלא יצויין, יושלם אוטומטית בהתאם לזמן הנוכחי.

isdst – סוג נתון: מס' שלם
ערך: 1או 0 או -1
dst = daylight saving time או בעברית, שעון קיץ.
מקבלת 1, אם התאריך הוא בזמן שעון הקיץ. 0, אם לא. -1, אם לא ידוע (ברירת המחדל)

year – יכולה לקבל מס' 4 ספרתי (1988 וכדומה) או מס' דו ספרתי (98, 04 וכדומה).
כאשר מעבירים בפרמטר, מס' דו ספרתי, php ממפה אותו בעצמה בצורה הבאה:
המס' 0-69 ייצגו את השנים 2000 – 2069, והמס' 70-99 ימופו לשנים 1970 – 1999
(מס' בעל 4 ספרות מייצג שנה מדוייקת, לכן הוא אינו ימופה.).
דוגמא:










1
2
3
4  








<?php
$timestamp = mktime(15, 13, 23, 4, 3, 2001);
Echo date("M d Y H:i:s", $timestamp);
?>


מה שעשינו כאן למעשה, בעזרת הפונקציה mktime, קיבלנו את ה timestamp של התאריך 3/4/2/001 15:13:23 והכנסנו אותו לתוך המשתנה $timestamp, ואז בעזרת הפונקציה date(), אליה שלחנו את המשתנה $timestamp, פירמטנו את התאריך והדפסנו אותו, וכך אמורה להראות התוצאה: Apr 3 2001 15:13:23.
הפונקציה mktime יכולה גם לקבל ערכים לא צפויים כמו:











1  








mktime(0, 0, 0, 3, 34, 2003)


מה שאומר שהתאריך שנתנו לה הוא 34/3/2003 00:00:00. לא הגיוני נכון?
אבל מכיוון שהפונקציה מחזירה את מס' השניות מתחילת תקופת היוניקס בעזרת אלגוריתם חישוב מסויים,
אז מס' השניות שהיא תחזיר, יהיה מס' השניות של התאריך עם התוספת, כלאמר, הדוגמא הזאת תחזיר את מס' השניות של התאריך 3/4/2003 00:00:00. למה? החודש ה 3(מרץ) בשנת 2003 מסתיים ב31, אבל אנחנו נתנו תאריך שעבר את ה 31 ב 3 ימים, לכן נכנסנו כבר אל החודש הבא. כך זה עובד גם בשעות, בדקות בשניות ובחודשים. כך גם ניתן לעשות עם ערכים שלילייםמאופסים (כאשר מדובר בחודשים ובימים),
דוגמא:










1  








mktime(0,0,0,4,0,2003)


מה שאומר שהתאריך הוא 0/4/2003 00:00:00, שוב לא הגיוני.
לכן ה timestamp שיוחזר, יהיה של התאריך 31/3/2003 00:00:00 ואם היינו נותנים במקום 0 את המס' -1, היינו מקבלים את של ה 30/3 וכן הלאה וכו'.
שתי העובדות, ש mktime יכולה לקבל ערכים לא צפויים ולהחזיר תאריך תקין בהתאמה וש mktime מחזירה את התאריך כ timestamp, דהיינו שניות מתחילת תקופת הUnix עד לתאריך המבוקש, מקנות לנו את היכולת להשתמש בפונקציה לשם ביצוע מניפולציות על התאריכים והזמנים ב php.
להוסיף לתאריך מסויים, אלמנטים מסויימים (ימים, שנים, חודשים, שעות, שניות ודקות) או להחסיר ממנו אלמנטים מסויימים למצוא את ההפרשים בין תארכים מסויימים בשניות דקות ימים וכו' ועוד אפשרויות שונות.

לדוגמא, ניצור פונקציה שתוסיף לנו פרמטר מסויים של ימים לתאריך כלשהו (פרמטר גם הוא) הפונקציה תחזיר לנו את ה timestamp של התאריך המתוקן (אפשר להחזיר גם את התאריך עצמו מפורמט בתור מחרוזת) :










1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19  








<?php

function addDate($date, $days)
{
/*
התאריך שיתקבל, יהיה בפורמט dd/mm/yyyy hh:mm:ss או dd/mm/yy בלבד
$days – מס' הימים שנוסיף נחסיר (מס' שלילי)
*/

    $date_separate = explode(" ", $date); // נפצל לתוך מערך את התאריך לאלמנט התאריך עצמו(dd/mm/yy) ולאלמנט השעה (hh:mm:ss)
    $dateE = explode("/", $date_separate[0]); // נפצל לתוך מערך את התאריך עצמו לימים חודשים ושנים
    $hourE = (isset($date_separate[1])) ? explode(":", $date_separate[1]) : array(0, 0, 0);
    // כאן בדקנו האם קיים כלל אלמנט השעה, או שהוכנס התאריך עצמו בלבד
    // במקרה שהוא קיים נפצל אותו למערך שכל תא יכיל את אחד האלמנטים שעות דקות ושניות
    // במקרה שהוא לא קיים, ניצור את המערך בכל זאת ונאפס כל תא
    $tstamp = mktime($hourE[0], $hourE[1], $hourE[2], $dateE[1], $dateE[0] + $days, $dateE[2]); // נחזיר את ה timestamp של התאריך החדש שיצרנו לתוך משתנהtstamp
    return($tstamp); // נחזיר את ערכו של tstamp
}

?>


עכשיו נזמן את הפונקציה בצורה הבאה:










1
2
3  








<?php
echo date("d/m/Y", addDate("15/2/2004", 3))
?>


השורה הזאת תדפיס את התאריך 18/2/2004.

בעזרת mktime(), נוכל גם לקבל את הפרש הזמנים בין תאריכים בשניות, מכיוון שיש לנו אותם בשניות, נוכל גם בעזרת פעולות מתמטיות לקבל אותם כדקות, שעות ימים ושנים.
דוגמא:










1
2
3  








<?php
 $delta_time = mktime(0,0,0, 3, 16, 2001) mktime(0,0,0, 3, 13, 2001)
?>


את ההפרש שקיבלנו, קיבלנו בשניות, לכן אם תרצה להפוך אותו לשעות יהיה עלינו לעשות זאת כך










1
2
3  








<?php
 $delta_time = $delta_time / (60*60)
?>


בשעה אחת יש 3600 שניות (60 שניות לדקה * 60 דקות בשעה)
כעת $delta_time מכיל את ההפרש בשעות, אם היינו רוצים את ההפרש בימים היינו עושים זאת כך:










1
2
3  








<?php
$delta_time = $delta_time / (60*60*24)
?>


גם כאן תוכלו ליצור פונקציה מסודרת שתחזיר את ההפרש לפי רצונכם, תקבל תאריכים בפורמט כלשהו ותפרק אותן לאלמנטים השונים.

הפונקציה getdate












1  








getdate([int timestamp])


Timestamp – פרמטר אופציונאלי, אם לא צויין timestamp, הפונקציה תשתמש ב timestamp הנוכחי.

הפונקציה מקבלת את מס' השניות מתחילת תקופת ה Unix, ומחזירה מערך, שכל אינדקס שלו מציין אלמנט בתאריך שהתקבל (בהתאם ל timestamp)
רשימת האינדקסים הקיימים הם:


  • Seconds – 0-59 השנייה בתאריך המתקבל
  • Hours – 0-23 השעה בתאריך המתקבל
  • Minutes – 0-59 הדקה בתאריך המתקבל
  • Year – השנה מיוצגת ב 4 ספרות (1987 וכד')
  • Mon – 1-12 מס' החודש
  • Month – שם החודש, כגון February וכד'
  • Mday – 1-31 מס' היום בחודש
  • Wday – מס' היום בשבוע כאשר 0 מציין את יום ראשון ו 6 את יום שבת
  • Yday – 0-366 מס' היום בשנה
  • Weekday – ייצוג טקסטאלי של היום בשבוע כגון Sunday, Monday וכו'
  • 0 – מחזיר את מס' השניות מתחילת תקופת ה unix

הפונקציה microtime












1  








microtime([bool float])


הפונקציה microtime מחזירה מחרוזת ובה שני אלמנטים מופרדים ברווח ביניהם, בצורה כזאת "micro_seconds seconds", seconds הוא למעשה ה timestamp הנוכחי, מס' השניות מאז תחילת תקופת ה Unix, ו micro_seconds הם המיקרו שניות.
המיקרו שניות והשניות יחדיו מרכיבים את הזמן המדוייק עד המיקרו-שניה שעבר מתחילת תקופת ה Unix עד הרגע הנוכחי.

ב microtime משתמשים בעיקר למדידת הזמן הלוקח לביצוע פעולה או מס' פעולות בסקריפט, כמו למשל אם רוצים לבדוק כמה זמן לקח לשרת לבצע סקריפט מסויים כלאמר כמה זמן לקח לעמוד להווצר בכדי לעשות זאת מדוייק, יש לבדוק את הזמן המדוייק(עד המיקרו-שניה) בתחילת הסקריפט, ואת הזמן המדוייק, בסיומו, ולאחר מכן לחסר את הסוף מההתחלה, ההפרש הוא הזמן שלקח לסקריפט להתבצע אך בכדי להגיע למס' שניות מדוייק עד המיקרו-שנייה, יש צורך לחבר את seconds ואת ה micro_seconds, למס' אחד עשרוני שיראה כך seconds.microseconds (דוג: 1080547848. 990329)
לשם כך ניצור פונקציה שתעשה את הפעולה הזאת,










1
2
3
4
5
6
7  








<?php
    function micro_time()
    {
        list($micro_sec, $sec) = explode(" ", microtime());
        return((float)$sec + (float)$micro_sec);
    }
?>


אם תדפיסו את sec תקבלו מס' שנראה בערך כך: 1080547848
אם תדפיסו את micro_sec תקבלו מס' שנראה בערך כך: 0.990329

כאשר חיברנו את שניהם קיבלנו מס' שנראה בערך כך: 1080547848. 990329
עכשיו כדי להשתמש בזה, ולמדוד את הזמן שלקח לעמוד מסויים להתבצע, נעשה כך:










1
2
3
4
5
6  








<?php
$start_time = micro_time();
// Page code
$end time = micro_time() start_time;
echo("Execute time:".$end_time);
?>


הפרמטר float הוא פרמטר בוליאני, אם הוא מכוון לtrue, הפונקציה תחזיר מלכתחילה מס' עשרוני המורכב ממס' השניות והמיקרו-שניות ואז לא נצטרך לכתוב פונקציה שתעשה זאת אבל הפרמטר הנ"ל נוסף רק החל מגרסא .0.05 של php ולכן בגרסאות נמוכות יותר, זה פשוט לא יעבור ועדיין יהיה הצורך לעשות זאת לבד.

אלו הן הפונקציות העיקריות והשימושיות ביותר בעבודה עם זמנים ב php, כמובן שישנן עוד מס' פונצקיות, אך לא ראיתי את הצורך לפרט עליהן מכיוון שאני אישית עד כה לא מצאתי בהן הרבה שימוש.

תכנום נעים!

תגיות: ,

תגובות בפייסבוק