Calendar.getInstance (TimeZone.getTimeZone („UTC”)) nie zwraca czasu UTC


106

Jestem naprawdę zdezorientowany wynikiem, który otrzymuję przy Calendar.getInstance(TimeZone.getTimeZone("UTC"))wywołaniu metody, zwraca czas IST.

Oto kod, którego użyłem

Calendar cal_Two = Calendar.getInstance(TimeZone.getTimeZone("UTC"));
System.out.println(cal_Two.getTime());

a otrzymałem odpowiedź:

Sat Jan 25 15:44:18 IST 2014

Próbowałem więc zmienić domyślną strefę czasową na UTC, a potem sprawdziłem, czy działa dobrze

Calendar cal_Two = Calendar.getInstance(TimeZone.getTimeZone("UTC"));
System.out.println(cal_Two.getTime());

TimeZone tz  = TimeZone.getDefault() ;
TimeZone.setDefault(TimeZone.getTimeZone("UTC"));
Calendar cal_Three = Calendar.getInstance();
System.out.println(cal_Three.getTime());
TimeZone.setDefault(tz);

Wynik:

Sat Jan 25 16:09:11 IST 2014
Sat Jan 25 10:39:11 UTC 2014

Czy coś mi umyka?

Odpowiedzi:


146

System.out.println(cal_Two.getTime())Wywołanie zwraca Dateod getTime(). To jest Datekonwertowane na ciąg znaków dla println, a ta konwersja użyje domyślnej ISTstrefy czasowej w twoim przypadku.

Musisz wyraźnie użyć, DateFormat.setTimeZone()aby wydrukować Datew wybranej strefie czasowej.

EDYCJA: Dzięki uprzejmości @Laurynas, rozważ to:

TimeZone timeZone = TimeZone.getTimeZone("UTC");
Calendar calendar = Calendar.getInstance(timeZone);
SimpleDateFormat simpleDateFormat = 
       new SimpleDateFormat("EE MMM dd HH:mm:ss zzz yyyy", Locale.US);
simpleDateFormat.setTimeZone(timeZone);

System.out.println("Time zone: " + timeZone.getID());
System.out.println("default time zone: " + TimeZone.getDefault().getID());
System.out.println();

System.out.println("UTC:     " + simpleDateFormat.format(calendar.getTime()));
System.out.println("Default: " + calendar.getTime());

Szukałem tego przez chwilę. Może tytuł nie jest wystarczająco wyraźny? Przy okazji, dzięki za pomoc
gavard.e

3
Możesz zaoszczędzić dużo czasu, jeśli pokażesz wynik System.out.println :)
Vasil Valchev

1
Rozumiem… dzięki… Ale nie rozumiem, w jaki sposób ustawienie strefy czasowej byłoby obowiązkiem klasy simpleDateFormat. Zmiana strefy czasowej zmienia rzeczywisty czas, a nie format. Zadaniem SimpleDateFormat jest po prostu sformatowanie daty, a nie manipulowanie czasem ...
angryITguy

Doskonała odpowiedź !!
Najib Ahmed Puthawala

To (konieczność ustawienia strefy czasowej programu formatującego) dostaję się za każdym razem, mimo że ustawiłem strefę czasową kalendarza.
Agi Hammerthief

17

java.util.Datejest niezależna od strefy czasowej. Gdy drukujesz, cal_Twomimo że Calendarinstancja ma ustawioną strefę czasową UTC, cal_Two.getTime()zwróci Dateinstancję, która nie ma strefy czasowej (i jest zawsze w domyślnej strefie czasowej)

Calendar cal_Two = Calendar.getInstance(TimeZone.getTimeZone("UTC"));
System.out.println(cal_Two.getTime());
System.out.println(cal_Two.getTimeZone());

Wynik:

 Sat Jan 25 16:40:28 IST 2014
    sun.util.calendar.ZoneInfo[id="UTC",offset=0,dstSavings=0,useDaylight=false,transitions=0,lastRule=null] 

Z javadoc witryny TimeZone.setDefault()

Ustawia TimeZone, który jest zwracany przez metodę getDefault. Jeśli zone ma wartość null, zresetuj wartość domyślną, którą miała pierwotnie podczas pierwszego uruchomienia maszyny wirtualnej.

W związku z tym przeniesienie setDefault()przed cal_Twozostanie utworzone, otrzymasz poprawny wynik.

TimeZone.setDefault(TimeZone.getTimeZone("UTC"));
Calendar cal_Two = Calendar.getInstance(TimeZone.getTimeZone("UTC"));
System.out.println(cal_Two.getTime());

Calendar cal_Three = Calendar.getInstance();
System.out.println(cal_Three.getTime());

Wynik:

Sat Jan 25 11:15:29 UTC 2014
Sat Jan 25 11:15:29 UTC 2014

6
Calendar currentTime = Calendar.getInstance(TimeZone.getTimeZone("UTC"));
currentTime.set(Calendar.ZONE_OFFSET, TimeZone.getTimeZone("UTC").getRawOffset());
Calendar calendar = Calendar.getInstance();
calendar.set(Calendar.HOUR_OF_DAY, currentTime.get(Calendar.HOUR_OF_DAY));
calendar.getTimeInMillis()

pracuje dla mnie


5

Zdecydowanie brakuje ci małej rzeczy, a to znaczy, że nie ustawiasz wartości domyślnej:

TimeZone.setDefault(TimeZone.getTimeZone("UTC"));

Tak więc kod wyglądałby następująco:

TimeZone.setDefault(TimeZone.getTimeZone("UTC"));
Calendar cal_Two = Calendar.getInstance(TimeZone.getTimeZone("UTC"));
System.out.println(cal_Two.getTime());

Objaśnienie : Jeśli chcesz zmienić strefę czasową, ustaw domyślną strefę czasową za pomocąTimeZone.setDefault()


0
    Following code is the simple example to change the timezone
public static void main(String[] args) {
          //get time zone
          TimeZone timeZone1 = TimeZone.getTimeZone("Asia/Colombo");
          Calendar calendar = new GregorianCalendar();
          //setting required timeZone
          calendar.setTimeZone(timeZone1);
          System.out.println("Time :" + calendar.get(Calendar.HOUR_OF_DAY)+":"+calendar.get(Calendar.MINUTE)+":"+calendar.get(Calendar.SECOND));

       }

jeśli chcesz zobaczyć listę stref czasowych, oto poniższy kod

public static void main(String[] args) {

    String[] ids = TimeZone.getAvailableIDs();
    for (String id : ids) {
        System.out.println(displayTimeZone(TimeZone.getTimeZone(id)));
    }

    System.out.println("\nTotal TimeZone ID " + ids.length);

}

private static String displayTimeZone(TimeZone tz) {

    long hours = TimeUnit.MILLISECONDS.toHours(tz.getRawOffset());
    long minutes = TimeUnit.MILLISECONDS.toMinutes(tz.getRawOffset())
                              - TimeUnit.HOURS.toMinutes(hours);
    // avoid -4:-30 issue
    minutes = Math.abs(minutes);

    String result = "";
    if (hours > 0) {
        result = String.format("(GMT+%d:%02d) %s", hours, minutes, tz.getID());
    } else {
        result = String.format("(GMT%d:%02d) %s", hours, minutes, tz.getID());
    }

    return result;

}

-6

Spróbuj użyć GMTzamiast UTC. Odnoszą się do tej samej strefy czasowej, ale nazwa GMTjest bardziej powszechna i może działać.


Korzystanie z GMT da takie same wyniki.
Jim
Korzystając z naszej strony potwierdzasz, że przeczytałeś(-aś) i rozumiesz nasze zasady używania plików cookie i zasady ochrony prywatności.
Licensed under cc by-sa 3.0 with attribution required.