2017-08-01 10 views
2

J'ai deux horodatages de l'époque, j'essaie de trouver le nombre de jours entre les deux horodatages.Nombre de jours entre deux jours d'époque en scala

C'est ce que j'ai maintenant:

dateFrom = inputEntry.getValue(inputFields(0).get).asInstanceOf[String].toLong 
dateTo =inputEntry.getValue(inputFields(1).get).asInstanceOf[String].toLong 

Exemple:

dateFrom dateTo  result 
1501583232 1501641000 1 
1501583232 1501986600 5 

Je commence avec deux dates d'époque ici

+2

Copie possible de [Obtenir le nombre de jours, semaines et mois depuis Epoch en Java] (https://stackoverflow.com/questions/6158053/get-the-number-of-days-weeks-and- months-since-epoch-in-java) –

+0

Ce n'est pas un doublon. Cette question commence par un compte de secondes de l'époque. –

+0

cela est vrai, mais il est facilement extensible pour compter les jours entre deux dates en soustrayant ces jours de l'époque –

Répondre

2

tl; dr

ChronoUnit.DAYS.between(… , …) 

Détails

Cela a été couvert plusieurs fois déjà sur Stack Overflow. Donc brièvement ici ...

Pour les valeurs date-heure, utilisez des objets date-heure. Utilisez uniquement les classes java.time, évitez les classes de date-heure héritées gênantes (Date, Calendrier, etc.).

Voulez-vous dire une différence de dates ou une différence de tranches de temps de 24 heures?

Je pars avec des dates ici. Tout d'abord, traduisez ce qui semble être le nombre de secondes entières écoulées depuis la date de référence de l'époque 1970-01-01T00: 00: 00Z jusqu'à un point de la chronologie en UTC.

Notez le L à la fin du littéral numérique pour indiquer un long plutôt que int.

Instant instant = Instant.ofEpochSecond(1_501_583_232L) ; 

Affectez le fuseau horaire pour lequel vous souhaitez prendre en compte les dates.

ZoneId z = ZoneId.of("America/Montreal") ; 
ZonedDateTime zdt = instant.atZone(z); 

Convertir en date seule.

LocalDate ld = zdt.toLocalDate() ; 

Obtenez différence.

long days = ChronoUnit.DAYS.between(ld , ld2) ; 
1

Pour obtenir les résultats souhaités, vous devez définir comment calculer la différence.

Prendre votre premier exemple (différence entre 1501583232 et 1501641000 devrait être 1 jour):

Les époques 1501583232 et 1501641000 sont le nombre de secondes écoulées depuis 1970-01-01T00:00Z, de sorte qu'ils sont équivalents à la date UTC suivante:

Notez que la différence entre eux est de 16 heures, 2 minutes et 48 secondes (donc moins d'un jour)
1501583232: 2017-08-01T10:27:12Z 
1501641000: 2017-08-02T02:30:00Z 

Si vous obtenez la différence en jours, techniquement, ce sera zéro.

Mais si l'on considère que les dates (2017-08-01 et 2017-08-02) et ignorer l'heure (heure/minute/seconde), la différence peut être zéro ou 1, selon le fuseau horaire que vous êtes.

Si vous ne considérez que les dates UTC (2017-08-01 et 2017-08-02), la différence est 1 jour.

Mais si vous prenez la même UTC dates ci-dessus dans America/Los_Angeles fuseau horaire, vous obtiendrez:

1501583232: 2017-08-01T03:27:12-07:00 
1501641000: 2017-08-01T19:30-07:00 

Maintenant, la différence est de zéro jour, peu importe si l'on considère que la date (les deux sont 2017-08-01), ou la date et l'heure (la différence d'heures sera de 16, moins d'un jour). Donc, vous devez définir comment vous allez calculer la différence (ne considérer que la date, ou la date et l'heure, et quel fuseau horaire sera utilisé).


Dans votre cas, il semble que vous ne considérant que la date et sans tenir compte du temps, mais on ne sait pas ce fuseau horaire qu'il utilise. Quoi qu'il en soit, vous pouvez utiliser 8 new java.time API de JDK pour cela (pour JDK < = 7 vous pouvez utiliser le ThreeTen Backport - Le code ci-dessous fonctionne pour les deux.La seule différence est le nom des paquets (en Java 8 est java.time et dans ThreeTen Backport (ou Android ThreeTenABP) est org.threeten.bp), mais les classes et méthodes noms sont les mêmes).

Le code est fondamentalement le même que @BasilBourque's answer, car il est très simple avec la nouvelle API (je voulais juste ajouter les informations ci-dessus).

D'abord, vous créez les Instant « s à partir des valeurs d'époque:

Instant instant1 = Instant.ofEpochSecond(1501583232L); 
Instant instant2 = Instant.ofEpochSecond(1501641000L); 

Si vous voulez que la différence compte tenu de la date et l'heure, vous pouvez utiliser:

ChronoUnit.DAYS.between(instant1, instant2); 

Le résultat sera zéro .

Si vous voulez considérer que les dates UTC (et ignorer le temps), il suffit de faire:

// convert to UTC and get just the date (day/month/year) 
LocalDate d1 = instant1.atZone(ZoneOffset.UTC).toLocalDate(); 
LocalDate d2 = instant2.atZone(ZoneOffset.UTC).toLocalDate(); 
long days = ChronoUnit.DAYS.between(d1, d2); 

Le résultat sera 1.

Pour convertir à un fuseau horaire différent (au lieu de UTC), utilisez la classe ZoneId:

// use a specific timezone 
ZoneId zone = ZoneId.of("Asia/Kolkata"); 
// convert the Instant to a timezone and get only the date 
LocalDate d1 = instant1.atZone(zone).toLocalDate(); 
LocalDate d2 = instant2.atZone(zone).toLocalDate(); 
long days = ChronoUnit.DAYS.between(d1, d2); 

Dans ce cas, la différence est de 1, mais comme je l'ai dit ci-dessus, différents fuseaux horaires peuvent produire des résultats différents (peut être zéro ou 1 - par exemple, en changeant le code ci-dessus à ZoneId.of("America/Los_Angeles"), le résultat est zéro).


Notez que l'API utilise IANA timezones names (toujours dans le format Region/City, comme Asia/Kolkata ou Europe/Berlin). Évitez d'utiliser les abréviations à 3 lettres (comme CST ou IST) car elles sont ambiguous and not standard.

Vous pouvez obtenir la liste des fuseaux horaires disponibles (et choisir celle qui correspond le mieux à votre système) en appelant le ZoneId.getAvailableZoneIds().

Vous pouvez également utiliser le fuseau horaire par défaut du système avec ZoneId.systemDefault(), mais cela peut être modifié sans préavis, même au moment de l'exécution, il est donc préférable d'en utiliser un spécifique.