2017-08-11 2 views
0

Je suis en train de réaliser ce qui suit:Obtenez le numéro de la semaine où les semaines commencent à compter du premier lundi en Avril jusqu'au premier lundi prochain Avril en PHP

Aux fins de déclaration nos numéros de semaine commencent dès le premier lundi en Avril chaque an.

Je crée un calendrier en utilisant PHP dans le format suivant:

MTWTFSS

A la fin de chaque ligne de ce mois, je veux afficher le numéro de la semaine, à partir de 1 où le premier lundi Avril sera la première semaine jusqu'au premier lundi d'avril prochain (l'année prochaine) où il recommence à partir de l'année suivante.

Je suis aux prises avec la logique - quelqu'un peut-il suggérer une solution?

Merci

EDIT voir mon code ci-dessous, au fond ce que je suis en train de faire est au lieu d'avoir le numéro de la semaine du 01 janvier ont depuis le premier lundi en Avril:

<?php 
$monthNames = Array("January", "February", "March", "April", "May",  "June", "July", 
"August", "September", "October", "November", "December"); 
?> 

<?php 
if (!isset($_REQUEST["month"])) $_REQUEST["month"] = date("n"); 
if (!isset($_REQUEST["year"])) $_REQUEST["year"] = date("Y"); 
?> 

<?php 
$cMonth = $_REQUEST["month"]; 
$cYear = $_REQUEST["year"]; 

$prev_year = $cYear; 
$next_year = $cYear; 
$prev_month = $cMonth-1; 
$next_month = $cMonth+1; 

if ($prev_month == 0) { 
    $prev_month = 12; 
    $prev_year = $cYear - 1; 
} 
if ($next_month == 13) { 
    $next_month = 1; 
    $next_year = $cYear + 1; 
} 
?> 

<table width="250"> 
<tr align="center"> 
<td bgcolor="#999999" style="color:#FFFFFF"> 
<table width="100%" border="0" cellspacing="0" cellpadding="0"> 
<tr> 
<td width="50%" align="left"> <a href="<?php echo $_SERVER["PHP_SELF"] . "?month=". $prev_month . "&year=" . $prev_year; ?>" style="color:#FFFFFF">Previous</a></td> 
<td width="50%" align="right"><a href="<?php echo $_SERVER["PHP_SELF"] . "?month=". $next_month . "&year=" . $next_year; ?>" style="color:#FFFFFF">Next</a> </td> 
</tr> 
</table> 
</td> 
</tr> 
<tr> 
<td align="center"> 
<table width="100%" border="0" cellpadding="2" cellspacing="2"> 
<tr align="center"> 
<td colspan="8" bgcolor="#999999" style="color:#FFFFFF"><strong><?php echo $monthNames[$cMonth-1].' '.$cYear; ?></strong></td> 
</tr> 
<tr> 
<td align="center" bgcolor="#999999" style="color:#FFFFFF"><strong>M</strong></td> 
<td align="center" bgcolor="#999999" style="color:#FFFFFF"><strong>T</strong></td> 
<td align="center" bgcolor="#999999" style="color:#FFFFFF"><strong>W</strong></td> 
<td align="center" bgcolor="#999999" style="color:#FFFFFF"><strong>T</strong></td> 
<td align="center" bgcolor="#999999" style="color:#FFFFFF"><strong>F</strong></td> 
<td align="center" bgcolor="#999999" style="color:#FFFFFF"><strong>S</strong></td> 
<td align="center" bgcolor="#999999" style="color:#FFFFFF"><strong>S</strong></td> 
<td align="center" bgcolor="#999999" style="color:#FFFFFF"><strong>Week No</strong></td> 
</tr> 


<?php 
$timestamp = mktime(0,0,0,$cMonth,1,$cYear); 
$maxday = date("t",$timestamp); 
$thismonth = getdate ($timestamp); 
//$startday = $thismonth['wday']; 
$startday = $thismonth['wday']-1; 

$firstDateMonth = 0; 

function roundToNearestW($int, $i) { 
    return ceil($int/$i) * $i; 
} 

if ($startday == -1) 
{ 
    $startday = 6; 
} 
$complete_cells = roundToNearestW($maxday+$startday,7); 
for ($i=0; $i<($complete_cells); $i++) { 
    if(($i % 7) == 0) 
    { 
     echo "<tr> 
     "; 
    } 
    if($i < $startday || $i >= $maxday+$startday) 
    { 
     echo "<td></td> 
     "; 
    } 
    else 
    { 
     if(($i - $startday + 1) > $firstDateMonth) 
     { 
      $firstDateMonth = ($i - $startday + 1); 
     } 
     echo "<td align='center' valign='middle' height='20px'>". ($i - $startday + 1) . "</td> 
     "; 
    } 
    if(($i % 7) == 6) 
    { 
     $weekDate = $cYear."-".$cMonth."-".$firstDateMonth; 
     $Caldate = new DateTime($weekDate); 
     $week = $Caldate->format("W"); 
     echo "<td align='center' valign='middle' height='20px'>WK ".$week."</td> 
     "; 
    } 
    if(($i % 7) == 6) 
    { 
     echo "</tr>"; 
     //firstDateMonth = 0; 
    } 

} 
?> 



</table> 
</td> 
</tr> 
</table> 

partiel crédit pour le calendrier ci-dessus (légèrement modifié moi-même le code) à: https://www.phpjabbers.com/how-to-make-a-php-calendar-php26-4.html

+1

Vous êtes censé inclure votre tentative de codage, même si elle est très mauvaise. L'affichage de votre code prouve que vous avez essayé de vous résoudre et montre combien de recherches vous avez effectuées avant de poster votre question. Actuellement, il semble que vous utilisiez SO comme un service de codage gratuit. Cela peut ou peut ne pas être vrai. De toute façon, votre question a besoin d'une modification. – mickmackusa

+0

Je n'ai jamais demandé de solution de code, je demandais seulement la logique! La réponse ci-dessous démontre la logique afin que je puisse comprendre ce que je suis reconnaissant. – Michael

+0

Ce n'est pas pertinent. Vous êtes toujours censé inclure votre tentative. Je ne t'appelle pas une mauvaise personne. Veuillez mettre à jour votre question Il peut être un semi-code mélangé qui a des commentaires où sont les composants logiques mais utilise également des boucles php de base et d'autres syntaxes réelles. Faire cette étape aide les gens à se résoudre tout en écrivant leur question - ce qui réduit le total des questions qui touchent SO. Lorsque les problèmes isolés ne peuvent pas être résolus par le PO, les volontaires peuvent faire des ajustements simples, plutôt que d'écrire un bloc complet de code à partir de zéro. Encore une fois, ne pas vous appeler une mauvaise personne. – mickmackusa

Répondre

1

Cela me semble moins alambiquée, avec moins de traitement dans la boucle. DateInterval('P7D') signifie simplement définir l'intervalle à 7 jours (1 semaine) - ce peut être la seule partie qui est légèrement confuse en raison de la syntaxe. DatePeriod() fait tout le dur travail pour vous.

code (Demo)

$year=2018; // $_GET['year']; 
$next=$year+1; 
$start=new DateTime(date('Y-m-d', strtotime("first Monday of April $year"))); 
$stop=new DateTime(date('Y-m-d', strtotime("first Monday of April $next"))); 
// there is a known behavior of DatePeriod to stop before $stop (...not contain it) 
// See http://au2.php.net/manual/en/class.dateperiod.php for explanations & workarounds 
$range=new DatePeriod($start,new DateInterval('P7D'),$stop); 
echo "<table>"; 
    echo "<tr>"; 
     echo "<th colspan=\"8\">Financial Calendar $year-$next</th>"; 
    echo "</tr>"; 
    echo "<tr>"; 
     echo "<th>M</th><th>T</th><th>W</th><th>T</th><th>F</th><th>S</th><th>S</th><th>#</th>"; 
    echo "</tr>"; 
    foreach ($range as $i=>$date) { 
     echo "<tr>"; 
      echo "<td></td><td></td><td></td><td></td><td></td><td></td><td></td><td>",++$i,"(",$date->format("Y-m-d"),")</td>"; 
     echo "</tr>"; 
    } 
echo "</table>"; 

sortie (unrendered):

<table> 
    <tr> 
     <th colspan="8">Financial Calendar 2018-2019</th> 
    </tr> 
    <tr> 
     <th>M</th><th>T</th><th>W</th><th>T</th><th>F</th><th>S</th><th>S</th><th>#</th> 
    </tr> 
    <tr> 
     <td></td><td></td><td></td><td></td><td></td><td></td><td></td><td>1(2018-04-02)</td> 
    </tr> 
    <tr> 
     <td></td><td></td><td></td><td></td><td></td><td></td><td></td><td>2(2018-04-09)</td> 
    </tr> 
    <tr> 
     <td></td><td></td><td></td><td></td><td></td><td></td><td></td><td>3(2018-04-16)</td> 
    </tr> 
    ... 
    <tr> 
     <td></td><td></td><td></td><td></td><td></td><td></td><td></td><td>50(2019-03-11)</td> 
    </tr> 
    <tr> 
     <td></td><td></td><td></td><td></td><td></td><td></td><td></td><td>51(2019-03-18)</td> 
    </tr> 
    <tr> 
     <td></td><td></td><td></td><td></td><td></td><td></td><td></td><td>52(2019-03-25)</td> 
    </tr> 
</table> 

Maintenant, je ne veux pas vous priver de la possibilité de développer ce code pour vous-même, donc je Arrêtez ici. Cela devrait vous donner un pied pour terminer ce projet à votre spécification souhaitée.

+0

Le code gentil et simple là! – Michael

+0

J'ai maintenant ajouté ma solution de code partiel – Michael

+0

Wow, je suis vraiment impressionné par certains des conseils de ce lien phpjabber. Si ma réponse ne résout pas votre problème, pouvez-vous clarifier quelle partie vous avez raccroché? Votre calendrier est-il interactif? Avez-vous des données à insérer dans les cellules de jour? – mickmackusa

1

J'espère que la logique suivante répondra à vos besoins.

<?php 

$begin = new DateTime(date('Y-m-d', strtotime('first Monday of April this year'))); 
$end  = new DateTime(date('Y-m-d', strtotime('last Monday of March next year'))); 
$interval = DateInterval::createFromDateString('1 week'); 

$weekNumberOfFirstMondayInApril = $begin->format('W'); 

foreach (new DatePeriod($begin, $interval, $end) as $dt) { 
    $phpWeekNum = $dt->format('W'); 

    $isFirstQuarter = ($phpWeekNum < $weekNumberOfFirstMondayInApril); 

    $businessWeekNum = $isFirstQuarter 
     ? ($phpWeekNum + (52 - $weekNumberOfFirstMondayInApril)) 
     : ($phpWeekNum - $weekNumberOfFirstMondayInApril) ; 

    echo 'Date: ' . $dt->format('l, Y-m-d') . PHP_EOL; 
    echo 'PHP week number: ' . $phpWeekNum . PHP_EOL; 
    echo 'Business week number: ' . ($businessWeekNum + 1) . PHP_EOL; 
    echo PHP_EOL; 
} 

Il est sortie est comme suit:

Date: Monday, 2017-04-03 
PHP week number: 14 
Business week number: 1 

    <snip> 

Date: Monday, 2017-12-25 
PHP week number: 52 
Business week number: 39 

Date: Monday, 2018-01-01 
PHP week number: 01 
Business week number: 40 

    <snip> 

Date: Monday, 2018-03-26 
PHP week number: 13 
Business week number: 52 
+0

Merci pour cela, je pense que je comprends le sens de la logique utilisée. J'ai juste besoin de construire maintenant ceci dans mon calendrier de sorte que à la fin de chaque rangée (chaque semaine) est affiche le numéro de semaine, je mettrai à jour avec n'importe quel progrès – Michael