2011-06-25 65 views
5

我不知道該如何去解決這個問題。我正在PHP中創建一個日曆,並且需要用戶能夠添加一個遵循以下規則的重複事件:如何找到月份的最後一個星期一

最後一個[DOW]的月份(所以最後[Mon/Tuesday/Wed/etc]周)

我有規則本身存儲,我只是不確定如何最好地推斷在PHP月的最後週一/週二/週三?我倒下了,就像我讓這件事比它需要的更復雜。

假設你有變量$month=4,$dow=3$year=2011我該如何做到最好?

回答

20

對於所有與日期有關的,你可以用適當的英語表達,但很難用數字表達,strtotime是你最好的朋友。

echo strtotime("last Monday of June 2011"); 

這會返回一個時間戳,您可以用作爲第二個參數date和喜歡得到一個合適的,人類可讀的日期。由於它是一個用C語言編寫的內置函數,這個解決方案比使用PHP編寫的幾乎任何其他東西都快得多(儘管我確信它在現實世界中並不重要)。

所以假設你有$month=4$dow=3$year=2011,你需要一個數組映射$month值,以他們的英語文本表示和另一個數組映射$dow值的文本表示。

+2

正如注意:確保你不會忘記'的'。 – cwallenpoole

+0

謝謝soo!我以爲我過於複雜了! – TH1981

0

我有一個通用函數來計算一個月的第n天。希望這可以幫助你解決你的問題。

function get_Nth_dow($dow, $occurence, $m, $y) 
{ 
    $numdays = date('t', mktime(0, 0, 0, $m, 1, $y)); 
    $add = 7 * ($occurence - 1); 
    $firstdow = date('w', mktime(0, 0, 0, $m, 1, $y)); 
    $diff = $firstdow - $dow; 

    $day_of_month = 1; 
    if ($diff > 0) 
    { 
     $day_of_month += ($add - $diff); 
    } 
    elseif ($diff < $numdays) 
    { 
     $day_of_month -= ($diff - $add); 
    } 

    return $day_of_month; 
} 

$DOW =星期幾(0 =星期日,6 =星期六)。

$X =發生(1 =第一,2 =第三等)。如果給定的月份沒有發生,那麼它將返回最後一個。例如,如果

你問週五第七屆發生,它會返回一個月的最後

週五。 $M =月 $Y =年

例,get_Nth_DOW(2,3,7,2009)將返回2009年7

0

第三個星期二這裏有一個選擇:

<? 
function lastDayOfMonth($month, $year) { 
    switch ($month) { 
     case 2: 
      # if year is divisible by 4 and not divisible by 100 
      if (($year % 4 == 0) && ($year % 100) > 0) 
       return 29; 
      # or if year is divisible by 400 
      if ($year % 400 == 0) 
       return 29; 
      return 28; 
     case 4: 
     case 6: 
     case 9: 
     case 11: 
      return 30; 
     default: 
      return 31; 
    } 
} 

function lastDayOfWeek($month, $year, $dow) { 
    $d = new DateTime(); 

    #Finding the last day of month 
    $d = $d->setDate($year, $month, lastDayOfMonth($month, $year)); 

    #Getting the day of week of last day of month 
    $date_parts = getdate($d->getTimestamp()); 

    $diff = 0; 

    #if we can't find the $dow in this week... (cause it would lie on next month) 
    if ($dow > $date_parts['wday']) { 
     # ...we go back a week. 
     $diff -= 7; 
    } 

    return $date_parts['mday'] + $diff + ($dow - $date_parts['wday']); 
} 

# checking the algorithm for this month... 
for ($i=0; $i < 7; $i++) { 
    echo lastDayOfWeek(6,2011,$i) . "<br>"; 
} 

?> 
相關問題