0

给定这两个 YYYYMM 字符串:

$start = "201301";
$end = "201303";

我想派生一个这样的数组:

array (
  0 => 
  array (
    0 => '20130101',
    1 => '20130131',
  ),
  1 => 
  array (
    0 => '20130201',
    1 => '20130228',
  ),
  2 => 
  array (
    0 => '20130301',
    1 => '20130331',
  ),
)

我已经用 date() 和 mktime() 尝试了一些东西,但到目前为止还没有什么像样的。

有什么好方法可以做到这一点?

4

7 回答 7

2

使用日期时间:

$start = "201301";
$end = "201303";

$dateNiceStart = substr($start,0,4).'-'.substr($start,4).'-01';
$dateNiceEnd = substr($end,0,4).'-'.substr($end,4).'-';

// Days count in month
$endDays = date('t',strtotime($dateNiceEnd.'01'));
$dateNiceEnd .= $endDays;

$startObj = new DateTime($dateNiceStart);
$endObj = new DateTime($dateNiceEnd);

$temp = clone $startObj;

$arr = array();
// Adding first month
//Using first day and last day
$temp->modify( 'first day of this month' );
$start = $temp->format('Ymd');
$temp->modify( 'last day of this month' );
$end = $temp->format('Ymd');

$arr[] = array($start, $end);
do{
    // for next month
    $temp->modify( 'first day of next month' );
    $start = $temp->format('Ymd');
    $temp->modify( 'last day of this month' );
    $end = $temp->format('Ymd');

    $arr[] = array($start, $end);

    // This line edited to work properly in different years, thanks to @Adidi
    $interval = $endObj->diff($temp)->format('%y%m%d');
}
while ($interval!=0);

print_R($arr);

主键是下/本月使用的第一天/最后一天。

于 2013-04-22T10:03:05.677 回答
1

http://www.php.net/manual/en/function.date.php

您需要的是格式字符串“t”:

t给定月份的天数 28 到 31

于 2013-04-22T09:50:06.833 回答
1

这是循环它的简单方法..

$start  = "201301";
$end    = "201303";

$start_time = strtotime(implode('-',str_split($start,4)));
$end_time = strtotime(implode('-',str_split($end,4)));

$array = array();
if($start_time <= $end_time){
    while($start_time <= $end_time){
        $month = date('F', $start_time);
        $array[] = array(
            date('Ymd', strtotime("first day of {$month}", $start_time)),
            date('Ymd', strtotime("last day of {$month}", $start_time)));
        $start_time = strtotime("next month", $start_time);
    }
}
于 2013-04-22T09:51:25.790 回答
0

您可以尝试使用这些功能:

function get_date_range ($start, $end) {

    $dates = array();

    $start = strtotime($start .'01');
    $end    = strtotime($end .'01');

    while ($start <= $end) {
        $dates [] = array(date('Ym01', $start), date('Ymt', $start));
        $start  = strtotime(add_month(date('Y-m-01', $start), 1));
    }

    return $dates;
}

function add_month($date_value, $months, $format = 'm/d/Y') {
    $date = new DateTime($date_value);
    $start_day = $date->format('j');

    $date->modify("+{$months} month");
    $end_day = $date->format('j');

    if ($start_day != $end_day)
        $date->modify('last day of last month');

    return $date->format($format);
}

$start = "201301";
$end    = "201303";

$dates = get_date_range($start, $end);

print_r($dates);

在这里,该add_month功能将帮助您避免在将一个月添加到 1 月 31 日时出现日期问题。

如果您使用strtotime它将在 1 月 31 日添加 1 个月时转到 3 月。输出将是:

Array
(
    [0] => Array
        (
            [0] => 2013-01-01
            [1] => 2013-01-31
        )

    [1] => Array
        (
            [0] => 2013-02-01
            [1] => 2013-02-28
        )

    [2] => Array
        (
            [0] => 2013-03-01
            [1] => 2013-03-31
        )

)

希望这可以帮助你:)

于 2013-04-22T10:08:43.343 回答
0

工作解决方案:

$start = "201301";
$end = "201309";

function getDateTimeByString($str_date){
    preg_match('/^([\d]{4})([\d]{2})$/',$str_date,$matches);
    $dt = null;
    if($matches){
        $dt = new DateTime();
        $dt->setDate($matches[1],$matches[2],1);   
    }
    return $dt;      
}


$start_dt = getDateTimeByString($start);
$end_dt = getDateTimeByString($end);

$output = array();

while($start_dt->getTimestamp() <= $end_dt->getTimestamp()){
    $arr = array(); 
    $arr[] = $start_dt->format('Ymd');
    $start_dt->modify('last day of this month');
    $arr[] = $start_dt->format('Ymd');

    $output[] = $arr;  

    $start_dt->modify('first day of next month');
}


print_r($output);

印刷:

Array
(
    [0] => Array
        (
            [0] => 20130101
            [1] => 20130131
        )

    [1] => Array
        (
            [0] => 20130201
            [1] => 20130228
        )

    [2] => Array
        (
            [0] => 20130301
            [1] => 20130331
        )

    [3] => Array
        (
            [0] => 20130401
            [1] => 20130430
        )

    [4] => Array
        (
            [0] => 20130501
            [1] => 20130531
        )

    [5] => Array
        (
            [0] => 20130601
            [1] => 20130630
        )

    [6] => Array
        (
            [0] => 20130701
            [1] => 20130731
        )

    [7] => Array
        (
            [0] => 20130801
            [1] => 20130831
        )

    [8] => Array
        (
            [0] => 20130901
            [1] => 20130930
        )

)
于 2013-04-22T10:00:50.237 回答
0

像这样的东西?

for($i=1;$i<=12;$i++) {
    $first = '2013'.($i<10 ? '0'.$i : $i).'01';
    $last = date('Ymt', strtotime($first));
    $myArray[] = array($first, $last);
}

未测试。

于 2013-04-22T09:42:50.657 回答
0

您可以像这样迭代几个月:

function date_range($start, $end)
{
    $start = strtotime("$start01");
    $end = strtotime("$end01");

    $res = array();

    while ($start < $end) {
        $next = strtotime("+1 month -1 day", $start);
        $res[] = array(
            date('Ymd', $start),
            date('Ymd', $next),
        );
        $start = $next;
    }

    return $res;
}
于 2013-04-22T09:43:35.060 回答