Calculer la différence de jours

Résolu
jobouille Messages postés 286 Date d'inscription   Statut Membre Dernière intervention   -  
jobouille Messages postés 286 Date d'inscription   Statut Membre Dernière intervention   -
Bonjour à tous !
Je vous explique mon problème, sur mon site j'affiche un message de la dernière connexion d'un membre (afin que les autres membres puissent voir quand es ce que ce membre a été dernièrement connecté).
Pour cela il y a une date dans la bdd de chaque membre lorsqu'il se connecte.

Donc pour afficher la dernière connexion, il faut faire la différence de la date de celle de la bdd par rapport à la date actuelle.

J'ai fais ce code (qui contient pas mal de if, ce qui me dérange) mais il y a un problème.

$datetime1 = strtotime($donnees['derniereCo']);
$now = date('Y-m-d H:i:s');
$datetime2 = strtotime($now);
           
$interval  = abs($datetime2 - $datetime1);
$hours= round($interval / 3600); 

if($hours < 24)
{
 $msg_derniereCo = "Aujourd'hui";
}
if($hours >= 24 AND $hours < 48)
{
 $msg_derniereCo = "Hier";
}
if($hours >= 48 AND $hours < 72)
{
 $msg_derniereCo = "Il y a 2 jours";
}
if($hours >= 72 AND $hours < 96)
{
 $msg_derniereCo = "Il y a 3 jours";
}
if($hours >= 96 AND $hours < 120)
{
 $msg_derniereCo = "Il y a 4 jours";
}
if($hours >= 120 AND $hours < 144)
{
 $msg_derniereCo = "Il y a 5 jours";
}
if($hours >= 144 AND $hours < 168)
{
 $msg_derniereCo = "Il y a 6 jours";
}
if($hours >= 168 AND $hours < 192)
{
 $msg_derniereCo = "Il y a 1 semaine";
}
if($hours >= 192)
{
 $msg_derniereCo = "Il y a plus d'une semaine !";
}


Me problème étant que si le membre se connecte un Mardi à 22h par exemple. Le lendemain (avant 22h) on verra "Dernière connexion : Aujourd'hui". Car mon code calcul les heures et pas les jours.

Il faudrait en fait calculer la différence des jours afin que dès que minuit passe, cela fasse 1 jour de plus.

Je ne sais pas si je me suis bien exprimé mais j'espère que vous saurez m'aider.

Merci et bonne journée/soirée.
A voir également:

2 réponses

NHenry Messages postés 15219 Date d'inscription   Statut Modérateur Dernière intervention   365
 
Déjà, tu peux simplifié en utilisant elseif :


if($hours < 24)
{
 $msg_derniereCo = "Aujourd'hui";
}
elseif($hours < 48)
{
 $msg_derniereCo = "Hier";
}
elseif($hours < 72)
{
 $msg_derniereCo = "Il y a 2 jours";
}
else
{
 $msg_derniereCo = "Trop longtemps";
}



Ensuite, tu peux aussi faire un tableau :
$Duree=array();
$Duree[]=array(24,"Aujourd'hui");
$Duree[]=array(48,"Hier");
...

Puis une boucle :
$Texte="";
for($i,$i<count($Duree);$i++)
    if($Duree[$i][0]>$hours)
        $Texte=$Duree[$i][1];
if($Texte=="")
    $Texte="Trop longtemps";

0
jobouille Messages postés 286 Date d'inscription   Statut Membre Dernière intervention   10
 
Je suis plutôt débutant et je n'ai pas très bien compris ce "tableau".

Merci de m'avoir répondu et il est vrai que je n'avais pas pensé à "raccourcir" le code de cette manière-ci.
Cependant le problème reste le même :/

Merci
0
NHenry Messages postés 15219 Date d'inscription   Statut Modérateur Dernière intervention   365
 
Pour le tableau, chaque :
$Duree[]=array(...,"...");
Ajoute une entrée à la fin du tableau.
Les entrées sont composées d'un autre tableau avec en premier, le nombre d'heure et en second le texte à afficher.

Ensuite la boucle va permettre de chercher l'entrée qui est la première à matcher (d'ailleurs, il y a un petit bug, voir plus bas dans mon message), si rien n'est trouvé, c'est que c'est hors tableau donc on affiche un texte par défaut.

    if($Duree[$i][0]>$hours)
        $Texte=$Duree[$i][1];

est à remplacer par :
    if($Duree[$i][0]>$hours)
    {
        $Texte=$Duree[$i][1];
        break;
    }
0
Utilisateur anonyme
 
Déjà pour gagner une ligne, au lieu de faire ça:

$now = date('Y-m-d H:i:s');
$datetime2 = strtotime($now);


La fonction time() est faite pour ça:

$datetime2 = time();


Et là avec le code que tu montres, tu peux comprimer encore plus:

$now = date('Y-m-d H:i:s');
$datetime2 = strtotime($now);
           
$interval  = abs($datetime2 - $datetime1);
$hours= round($interval / 3600); 


Devient:

$hours = round((time() - $datetime1)/ 3600);


Car si ton système est bien foutu, normalement un membre ne peut pas écrire un message dans le futur, du coup le abs n'est pas utile car la date du message sera toujours inférieure à celle actuelle.

Mais vaut mieux faire un floor, car un round arrondi au dessus si c'est supérieur à .5, donc tu peux avoir il y a 2 jours au lieu de hier.

Donc:

$hours = floor((time() - $datetime1)/ 3600);


Et petit conseille, enregistre les dates avec le timestamp directement et non la date, le timestamp est plus simple à utiliser. Du moins tu en fait un peu ce que tu veux car, si tu veux par exemple juste avoir le jour (Lundi, Mardi...) Tu dois convertir ta date en timestamp puis la reconvertir pour avoir le jour.

Après pour éviter tout les if il y a le switch/case ( https://www.php.net/manual/fr/control-structures.switch.php )

Il vas tester une valeur avec plusieurs résultat, et si l'un d'eux est correct, il exécute la commande associé, car si tu regardes tu utilises des multiples de 24, du coup ça revient à 1x24, 2x24.

Ce qui donne:

switch (ceil($hours/24)) {
 case 0:
  $msg_derniereCo = "Aujourd'hui";
  break;
 case 1:
  $msg_derniereCo = "Hier";
  break;
 case 2:
  $msg_derniereCo = "Il y a 2 jours";
  break;
 case 3:
  $msg_derniereCo = "Il y a 3 jours";
  break;
 case 4:
  $msg_derniereCo = "Il y a 4 jours";
  break;
 case 5:
  $msg_derniereCo = "Il y a 5 jours";
  break;
 case 6:
  $msg_derniereCo = "Il y a 6 jours";
  break;
 case 7:
  $msg_derniereCo = "Il y a 1 semaine";
  break;
 default:
  $msg_derniereCo = "Il y a plus d'une semaine !";
  break;
}


On peut même aller plus loin car si tu remarques la case 2, 3, 4, 5 et 6 on le même message, on obtient alors:

switch (ceil($hours/24)) {
 case 0:
  $msg_derniereCo = "Aujourd'hui";
  break;
 case 1:
  $msg_derniereCo = "Hier";
  break;
 case 2:
 case 3:
 case 4:
 case 5:
 case 6:
  $msg_derniereCo = "Il y a ".floor($hours/24)." jours";
  break;
 case 7:
  $msg_derniereCo = "Il y a 1 semaine";
  break;
 default:
  $msg_derniereCo = "Il y a plus d'une semaine !";
  break;
}


Enfin pour répondre à ton problème , tu peux comparer le jour, si on est le 03 ou le 04:

case 0:
 if (date('d') == date('d', $datetime1)) {
  $msg_derniereCo = "Aujourd'hui";
 } else {
  $msg_derniereCo = "Hier";
 }
 break;


Et si tu veux encore plus comprimé, il y a la condition ternaire:

case 0:
 $msg_derniereCo = (date('d') == date('d', $datetime1)) ? "Aujourd'hui" : "Hier" ;
 break;


J'espère t'avoir aidé et appris des trucs, au final ton code peut ressembler à ça:

$datetime1 = strtotime($donnees['derniereCo']);
$hours = floor(floor((time() - $datetime1)/ 3600)/24);
switch ($hours) {
 case 0:
  $msg_derniereCo = (date('d') == date('d', $datetime1)) ? "Aujourd'hui" : "Hier" ;
  break;
 case 1:
  $msg_derniereCo = "Hier";
  break;
 case 2:
 case 3:
 case 4:
 case 5:
 case 6:
  $msg_derniereCo = "Il y a ".$hours." jours";
  break;
 case 7:
  $msg_derniereCo = "Il y a 1 semaine";
  break;
 default:
  $msg_derniereCo = "Il y a plus d'une semaine !";
  break;
}
0
jobouille Messages postés 286 Date d'inscription   Statut Membre Dernière intervention   10
 
Merci beaucoup de votre réponse complète !
Cela m'a effectivement appris pas mal de chose.

Cependant le message affiché est toujours "Il y a plus d'une semaine !".
Comme s'il prenait cette valeur par défaut sans tenir compte des autres.
J'ai pourtant changer ma colonne en TIMESTAMP (et non datetime) et je n'ai pas modifié le code :
$datetime1 = $donnees['derniereCo'];
$hours = floor(floor((time() - $datetime1)/ 3600)/24);
switch ($hours) {
case 0:
$msg_derniereCo = (date('d') == date('d', $datetime1)) ? "Aujourd'hui" : "Hier" ;
break;
case 1:
$msg_derniereCo = "Hier";
break;
case 2:
case 3:
case 4:
case 5:
case 6:
$msg_derniereCo = "Il y a ".$hours." jours";
break;
case 7:
$msg_derniereCo = "Il y a 1 semaine";
break;
default:
$msg_derniereCo = "Il y a plus d'une semaine !";
break;
}


Encore merci de votre aide :D
0
Utilisateur anonyme
 
Vérifie le Timestamp alors, il y a un truc incorrect, car si tu remplaces:

$datetime1 = $donnees['derniereCo'];


Par:

$datetime1 = strtotime('-2 hours');


Ou:

$datetime1 = strtotime('-2 days');


Ça retourne aujourd'hui ou il y a 2 jours
0
jobouille Messages postés 286 Date d'inscription   Statut Membre Dernière intervention   10
 
Effectivement ça me met "Aujourd'hui" avec le premier datetime1 et "Il y a 2 jours" avec l'autre.

Comment je peux faire pour vérifier le timestamp ?

Merci
0
Utilisateur anonyme
 
Fait un var_dump de ta variable donc var_dump($datetime1); Comme ça tu veras le contenu de la variable.
0
jobouille Messages postés 286 Date d'inscription   Statut Membre Dernière intervention   10
 
Ça m'affiche ceci : string(19) "2015-08-04 00:01:39"
Il y a donc ce " string(19) " suivi de la date de la bdd du membre.
0