Disons que j'ai une date au format suivant: 2010-12-11 (year-mon-day)
Avec PHP, je souhaite incrémenter la date d'un mois et je souhaite que l'année soit automatiquement incrémentée, si nécessaire (c'est-à-dire incrémentée de décembre 2012 à janvier 2013).
Cordialement.
$time = strtotime("2010.12.11");
$final = date("Y-m-d", strtotime("+1 month", $time));
// Finally you will have the date you're looking for.
J'avais besoin de fonctionnalités similaires, sauf pour un cycle mensuel (plus mois, moins 1 jour). Après avoir cherché S.O. pendant un moment, j'ai pu concevoir cette solution plug-n-play:
function add_months($months, DateTime $dateObject)
{
$next = new DateTime($dateObject->format('Y-m-d'));
$next->modify('last day of +'.$months.' month');
if($dateObject->format('d') > $next->format('d')) {
return $dateObject->diff($next);
} else {
return new DateInterval('P'.$months.'M');
}
}
function endCycle($d1, $months)
{
$date = new DateTime($d1);
// call second function to add the months
$newDate = $date->add(add_months($months, $date));
// goes back 1 day from date, remove if you want same day of month
$newDate->sub(new DateInterval('P1D'));
//formats final date to Y-m-d form
$dateReturned = $newDate->format('Y-m-d');
return $dateReturned;
}
Exemple:
$startDate = '2014-06-03'; // select date in Y-m-d format
$nMonths = 1; // choose how many months you want to move ahead
$final = endCycle($startDate, $nMonths); // output: 2014-07-02
Utilisez DateTime::add
.
$start = new DateTime("2010-12-11", new DateTimeZone("UTC"));
$month_later = clone $start;
$month_later->add(new DateInterval("P1M"));
J'ai utilisé clone parce que add modifie l'objet d'origine, ce qui peut ne pas être souhaité.
strtotime( "+1 month", strtotime( $time ) );
cela retourne un horodatage qui peut être utilisé avec la fonction date
J'utilise de cette façon: -
$occDate='2014-01-28';
$forOdNextMonth= date('m', strtotime("+1 month", strtotime($occDate)));
//Output:- $forOdNextMonth=02
/*****************more example****************/
$occDate='2014-12-28';
$forOdNextMonth= date('m', strtotime("+1 month", strtotime($occDate)));
//Output:- $forOdNextMonth=01
//***********************wrong way**********************************//
$forOdNextMonth= date('m', strtotime("+1 month", $occDate));
//Output:- $forOdNextMonth=02; //instead of $forOdNextMonth=01;
//******************************************************************//
(date('d') > 28) ? date("mdY", strtotime("last day of next month")) : date("mdY", strtotime("+1 month"));
Cela compensera pour février et les 31 autres jours. Vous pourriez bien sûr faire beaucoup plus de vérifications pour obtenir plus de précision pour 'ce jour du mois prochain' formats de date relatifs (ce qui ne fonctionne pas tristement, voir ci-dessous), et vous pourriez aussi bien utiliser DateTime.
DateInterval('P1M')
et strtotime("+1 month")
ajoutent essentiellement aveuglément 31 jours, quel que soit le nombre de jours du mois suivant.
Vous pouvez utiliser DateTime::modify
comme ceci:
$date = new DateTime('2010-12-11');
$date->modify('+1 month');
Voir les documentations:
S'il vous plaît d'abord vous définissez votre format de date comme comme 12-12-2012
Après utilisation, cette fonction fonctionne correctement.
$date = date('d-m-Y',strtotime("12-12-2012 +2 Months");
Ici 12-12-2012 est votre date et +2 mois est l’incrément du mois;
Vous avez également incrémenté d'année, date
strtotime("12-12-2012 +1 Year");
Ans est le 12-12-2013
Merci Jason, votre message a été très utile. Je l'ai reformaté et ajouté plus de commentaires pour m'aider à tout comprendre. Au cas où cela aiderait quelqu'un, je l'ai posté ici:
function cycle_end_date($cycle_start_date, $months) {
$cycle_start_date_object = new DateTime($cycle_start_date);
//Find the date interval that we will need to add to the start date
$date_interval = find_date_interval($months, $cycle_start_date_object);
//Add this date interval to the current date (the DateTime class handles remaining complexity like year-ends)
$cycle_end_date_object = $cycle_start_date_object->add($date_interval);
//Subtract (sub) 1 day from date
$cycle_end_date_object->sub(new DateInterval('P1D'));
//Format final date to Y-m-d
$cycle_end_date = $cycle_end_date_object->format('Y-m-d');
return $cycle_end_date;
}
//Find the date interval we need to add to start date to get end date
function find_date_interval($n_months, DateTime $cycle_start_date_object) {
//Create new datetime object identical to inputted one
$date_of_last_day_next_month = new DateTime($cycle_start_date_object->format('Y-m-d'));
//And modify it so it is the date of the last day of the next month
$date_of_last_day_next_month->modify('last day of +'.$n_months.' month');
//If the day of inputted date (e.g. 31) is greater than last day of next month (e.g. 28)
if($cycle_start_date_object->format('d') > $date_of_last_day_next_month->format('d')) {
//Return a DateInterval object equal to the number of days difference
return $cycle_start_date_object->diff($date_of_last_day_next_month);
//Otherwise the date is easy and we can just add a month to it
} else {
//Return a DateInterval object equal to a period (P) of 1 month (M)
return new DateInterval('P'.$n_months.'M');
}
}
$cycle_start_date = '2014-01-31'; // select date in Y-m-d format
$n_months = 1; // choose how many months you want to move ahead
$cycle_end_date = cycle_end_date($cycle_start_date, $n_months); // output: 2014-07-02
Toutes les solutions présentées ne fonctionnent pas correctement.
strtotime () et DateTime :: add ou DateTime :: modify donnent des résultats parfois invalides.
Exemples:
- 31.08.2019 + 1 mois donne 01.10.2019 au lieu du 30.09.2019
- 29.02.2020 + 1 an donne le 01.03.2021 au lieu du 28.02.2021
(testé sur PHP 5.5, PHP 7.3)
Voici ma fonction basée sur idée postée par Angelo qui résout le problème:
// $time - unix time or date in any format accepted by strtotime() e.g. 2020-02-29
// $days, $months, $years - values to add
// returns new date in format 2021-02-28
function addTime($time, $days, $months, $years)
{
// Convert unix time to date format
if (is_numeric($time))
$time = date('Y-m-d', $time);
try
{
$date_time = new DateTime($time);
}
catch (Exception $e)
{
echo $e->getMessage();
exit;
}
if ($days)
$date_time->add(new DateInterval('P'.$days.'D'));
// Preserve day number
if ($months or $years)
$old_day = $date_time->format('d');
if ($months)
$date_time->add(new DateInterval('P'.$months.'M'));
if ($years)
$date_time->add(new DateInterval('P'.$years.'Y'));
// Patch for adding months or years
if ($months or $years)
{
$new_day = $date_time->format("d");
// The day is changed - set the last day of the previous month
if ($old_day != $new_day)
$date_time->sub(new DateInterval('P'.$new_day.'D'));
}
// You can chage returned format here
return $date_time->format('Y-m-d');
}
Exemples d'utilisation:
echo addTime('2020-02-29', 0, 0, 1); // add 1 year (result: 2021-02-28)
echo addTime('2019-08-31', 0, 1, 0); // add 1 month (result: 2019-09-30)
echo addTime('2019-03-15', 12, 2, 1); // add 12 days, 2 months, 1 year (result: 2019-09-30)
function dayOfWeek($date){
return DateTime::createFromFormat('Y-m-d', $date)->format('N');
}
Exemples d'utilisation:
echo dayOfWeek(2016-12-22);
// "4"
echo dayOfWeek(date('Y-m-d'));
// "4"
Pour ceux qui recherchent une réponse à n'importe quel format de date.
echo date_create_from_format('d/m/Y', '15/04/2017')->add(new DateInterval('P1M'))->format('d/m/Y');
Il suffit de changer le format de la date.
$date = strtotime("2017-12-11");
$newDate = date("Y-m-d", strtotime("+1 month", $date));
Si vous voulez incrémenter par jours, vous pouvez aussi le faire
$date = strtotime("2017-12-11");
$newDate = date("Y-m-d", strtotime("+5 day", $date));