Comment soustraire X day d'un objet Date en Java?


147

Je veux faire quelque chose comme:

Date date = new Date(); // current date
date = date - 300; // substract 300 days from current date and I want to use this "date"

Comment faire?


4
Remarque obligatoire "Use Joda Time".
Steve McLeod

1
Les liens suivants pourraient vous être utiles. [Entrez la description du lien ici] [1] [entrez la description du lien ici] [2] [1]: stackoverflow.com/questions/212321/… [2]: stackoverflow.com/questions/ 2623610 /…
Ami

FYI, les anciennes classes de date-heure gênantes telles que java.util.Datemaintenant héritées , supplantées par les classes java.time .
Basil Bourque

Réponses:


280

Java 8 et versions ultérieures

Avec le changement d'API de date et d'heure de Java 8, utilisez LocalDate

LocalDate date = LocalDate.now().minusDays(300);

De même, vous pouvez avoir

LocalDate date = someLocalDateInstance.minusDays(300);

Reportez-vous à https://stackoverflow.com/a/23885950/260990 pour la traduction entre java.util.Date <--> java.time.LocalDateTime

Date in = new Date();
LocalDateTime ldt = LocalDateTime.ofInstant(in.toInstant(), ZoneId.systemDefault());
Date out = Date.from(ldt.atZone(ZoneId.systemDefault()).toInstant());

Java 7 et versions antérieures

Utiliser Calendarla add()méthode de

Calendar cal = Calendar.getInstance();
cal.setTime(dateInstance);
cal.add(Calendar.DATE, -30);
Date dateBefore30Days = cal.getTime();

22
Il s'agit de définir votre date personnalisée, au cas où vous ne voudriez pas tenir compte de la date actuelle
Jigar Joshi

11
La gestion des dates de Java est tellement gonflée!
digory doo

1
C'est une réponse vieille de 4 ans. de nouvelles modifications de l'API DateTime ont été apportées aux versions récentes de celui-ci. Je vais éditer la réponse
Jigar Joshi

Pour votre information, les classes date de temps anciens gênants tels que java.util.Date, java.util.Calendaret java.text.SimpleTextFormatsont maintenant héritage , supplanté par les java.time classes. Voir le didacticiel d'Oracle .
Basil Bourque

@JigarJoshi, ce serait formidable si vous mettiez à jour votre réponse avec l'API Java 8. Votre réponse est celle que les gens voient en premier.
jotaen

47

@JigarJoshi c'est la bonne réponse, et bien sûr aussi la recommandation @Tim à utiliser. joda-time .

Je veux seulement ajouter plus de possibilités pour soustraire des jours d'un java.util.Date.

Apache-commons

Une possibilité est d'utiliser apache-commons-lang . Vous pouvez le faire DateUtilscomme suit:

Date dateBefore30Days = DateUtils.addDays(new Date(),-30);

Bien sûr, ajoutez la commons-langdépendance pour ne faire que soustraire la date, ce n'est probablement pas une bonne option, mais si vous l'utilisez déjà, commons-langc'est un bon choix. Il y a aussi des méthodes pratiques pour addYears, addMonths, addWeekset ainsi de suite, jetez un oeil à l' api ici .

Java 8

Une autre possibilité est de profiter des nouveautés LocalDatede Java 8 en utilisant la minusDays(long days)méthode:

LocalDate dateBefore30Days = LocalDate.now(ZoneId.of("Europe/Paris")).minusDays(30);

Il ne sert à rien d'utiliser LocalDateTimecar cette classe n'a pas de concept de fuseau horaire ni de décalage par rapport à UTC. Utilisez-le uniquement lorsque la zone / le décalage est inconnu ou non pertinent. Au lieu de cela, utilisez LocalDateet passez a ZoneIdlors de l'appel de sa nowméthode. Voir la bonne réponse de Jacob van Lingen.
Basil Bourque

1
@BasilBourque Après votre avis, je vérifie l'api et vous avez tout à fait raison, donc je mets à jour la réponse. Merci.
albciff

Brian Montellano aimerait faire un commentaire: il ne devrait pas y sen avoir DateUtils, c'est juste DateUtil.
Ole VV

@ OleV.V. Brian Montellano a tort, vous pouvez consulter la DateUtilsdocumentation
Albciff

33

Utilisez simplement ceci pour obtenir la date avant 300 jours, remplacez 300 par vos jours:

Date date = new Date(); // Or where ever you get it from
Date daysAgo = new DateTime(date).minusDays(300).toDate();

Ici,

DateTime est org.joda.time.DateTime;

Date est java.util.Date


7
Le projet Joda-Time est maintenant en mode maintenance et conseille la migration vers les classes java.time .
Basil Bourque

13

API Java 8 Time:

Instant now = Instant.now(); //current date
Instant before = now.minus(Duration.ofDays(300));
Date dateBefore = Date.from(before);

Je dois dire API Java 8, pas 7. Et mentionner le package java.timepourrait aider. De plus, une discussion / explication est généralement attendue sur Stack Overflow plutôt qu'un simple extrait de code. Vous devez absolument expliquer Durationcar c'est la valeur ajoutée de votre réponse par rapport à celle de van Lingen .
Basil Bourque

Java 8 de cause, corrigé
Grigory Kislin

si proche, mais devrait être pour modifier un objet de date arbitraire, pas "maintenant"
bharal

9

Comme vous pouvez le voir ICI , vous pouvez faire beaucoup de manipulations. Voici un exemple montrant ce que vous pourriez faire!

DateFormat dateFormat = new SimpleDateFormat("yyyy/MM/dd HH:mm:ss");
Calendar cal = Calendar.getInstance();

//Add one day to current date.
cal.add(Calendar.DATE, 1);
System.out.println(dateFormat.format(cal.getTime()));

//Substract one day to current date.
cal = Calendar.getInstance();
cal.add(Calendar.DATE, -1);
System.out.println(dateFormat.format(cal.getTime()));

/* Can be Calendar.DATE or
*  Calendar.MONTH, Calendar.YEAR, Calendar.HOUR, Calendar.SECOND
*/

@Jigar Joshi: Je n'ai pas vu votre réponse ... Dois-je supprimer la mienne?
waldyr.ar

Pour info, les anciennes classes de date-heure terriblement gênantes telles que java.util.Date, java.util.Calendaret java.text.SimpleDateFormatsont maintenant héritées , supplantées par les classes java.time intégrées à Java 8 et versions ultérieures. Voir le didacticiel d'Oracle .
Basil Bourque

9

Avec Java 8, c'est vraiment simple maintenant:

 LocalDate date = LocalDate.now().minusDays(300);

Un excellent guide de la nouvelle API peut être trouvé ici .


4
Je suggère de toujours passer le fuseau horaire optionnel (ou offset-from-UTC) à cette nowméthode. S'il est omis, le fuseau horaire par défaut actuel de la JVM est appliqué implicitement et silencieusement. Cette valeur par défaut est hors de votre contrôle et peut changer à tout moment, même pendant l' exécution. Exemple: LocalDate.now( ZoneId.of( "America/Montreal" ).
Basil Bourque

doit être sur un objet de date arbitraire selon la question, pas "maintenant"
bharal

1

J'ai créé une fonction pour faciliter la tâche.

  • Pendant 7 jours après la dateString: dateCalculate(dateString,"yyyy-MM-dd",7);

  • Pour obtenir 7 jours jusqu'à dateString: dateCalculate(dateString,"yyyy-MM-dd",-7);


public static String dateCalculate(String dateString, String dateFormat, int days) {
    Calendar cal = Calendar.getInstance();
    SimpleDateFormat s = new SimpleDateFormat(dateFormat);
    try {
        cal.setTime(s.parse(dateString));
    } catch (ParseException e) {
        e.printStackTrace();
    }
    cal.add(Calendar.DATE, days);
    return s.format(cal.getTime());
}

Cette utilisation Réponse des cours à temps de date gênants anciens tels que java.util.Date, java.util.Calendaret java.text.SimpleDateFormatqui sont maintenant héritage , supplanté par les java.time classes. Voir le didacticiel d'Oracle .
Basil Bourque

La question implique des objets date-heure, pas de génération de chaînes. En passant, LocalDate.parse( "2017-01-23").plusWeeks( 1 )c'est plus simple que d'écrire votre propre méthode et est plus auto-documenté.
Basil Bourque

0

Vous pouvez facilement soustraire avec le calendrier avec SimpleDateFormat

 public static String subtractDate(String time,int subtractDay) throws ParseException {


        Calendar cal = Calendar.getInstance();
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm", Locale.ENGLISH);
        cal.setTime(sdf.parse(time));
        cal.add(Calendar.DATE,-subtractDay);
        String wantedDate = sdf.format(cal.getTime());

        Log.d("tag",wantedDate);
        return wantedDate;

    }

-4
c1.set(2017, 12 , 01); //Ex: 1999 jan 20    //System.out.println("Date is : " + sdf.format(c1.getTime()));
  c1.add(Calendar.MONTH, -2); // substract 1 month
  System.out.println
  ("Date minus 1 month : "
      + sdf.format(c1.getTime()));

2
Bienvenue à SO. Veuillez vous abstenir de répondre uniquement au code. Voir stackoverflow.com/help/how-to-answer . Et veuillez formater votre code.
Uwe Allner
En utilisant notre site, vous reconnaissez avoir lu et compris notre politique liée aux cookies et notre politique de confidentialité.
Licensed under cc by-sa 3.0 with attribution required.