< prev index next >

src/java.base/share/classes/java/time/ZoneOffset.java

Print this page


   1 /*
   2  * Copyright (c) 2012, 2013, Oracle and/or its affiliates. All rights reserved.
   3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
   4  *
   5  * This code is free software; you can redistribute it and/or modify it
   6  * under the terms of the GNU General Public License version 2 only, as
   7  * published by the Free Software Foundation.  Oracle designates this
   8  * particular file as subject to the "Classpath" exception as provided
   9  * by Oracle in the LICENSE file that accompanied this code.
  10  *
  11  * This code is distributed in the hope that it will be useful, but WITHOUT
  12  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  13  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  14  * version 2 for more details (a copy is included in the LICENSE file that
  15  * accompanied this code).
  16  *
  17  * You should have received a copy of the GNU General Public License version
  18  * 2 along with this work; if not, write to the Free Software Foundation,
  19  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  20  *
  21  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  22  * or visit www.oracle.com if you need additional information or have any


 358      * @param minutes  the time-zone offset in minutes, from 0 to &plusmn;59
 359      * @param seconds  the time-zone offset in seconds, from 0 to &plusmn;59
 360      * @throws DateTimeException if the offset is not in the required range
 361      */
 362     private static void validate(int hours, int minutes, int seconds) {
 363         if (hours < -18 || hours > 18) {
 364             throw new DateTimeException("Zone offset hours not in valid range: value " + hours +
 365                     " is not in the range -18 to 18");
 366         }
 367         if (hours > 0) {
 368             if (minutes < 0 || seconds < 0) {
 369                 throw new DateTimeException("Zone offset minutes and seconds must be positive because hours is positive");
 370             }
 371         } else if (hours < 0) {
 372             if (minutes > 0 || seconds > 0) {
 373                 throw new DateTimeException("Zone offset minutes and seconds must be negative because hours is negative");
 374             }
 375         } else if ((minutes > 0 && seconds < 0) || (minutes < 0 && seconds > 0)) {
 376             throw new DateTimeException("Zone offset minutes and seconds must have the same sign");
 377         }
 378         if (Math.abs(minutes) > 59) {
 379             throw new DateTimeException("Zone offset minutes not in valid range: abs(value) " +
 380                     Math.abs(minutes) + " is not in the range 0 to 59");
 381         }
 382         if (Math.abs(seconds) > 59) {
 383             throw new DateTimeException("Zone offset seconds not in valid range: abs(value) " +
 384                     Math.abs(seconds) + " is not in the range 0 to 59");
 385         }
 386         if (Math.abs(hours) == 18 && (Math.abs(minutes) > 0 || Math.abs(seconds) > 0)) {
 387             throw new DateTimeException("Zone offset not in valid range: -18:00 to +18:00");
 388         }
 389     }
 390 
 391     /**
 392      * Calculates the total offset in seconds.
 393      *
 394      * @param hours  the time-zone offset in hours, from -18 to +18
 395      * @param minutes  the time-zone offset in minutes, from 0 to &plusmn;59, sign matches hours and seconds
 396      * @param seconds  the time-zone offset in seconds, from 0 to &plusmn;59, sign matches hours and minutes
 397      * @return the total in seconds
 398      */
 399     private static int totalSeconds(int hours, int minutes, int seconds) {
 400         return hours * SECONDS_PER_HOUR + minutes * SECONDS_PER_MINUTE + seconds;
 401     }
 402 
 403     //-----------------------------------------------------------------------
 404     /**
 405      * Obtains an instance of {@code ZoneOffset} specifying the total offset in seconds
 406      * <p>
 407      * The offset must be in the range {@code -18:00} to {@code +18:00}, which corresponds to -64800 to +64800.
 408      *
 409      * @param totalSeconds  the total time-zone offset in seconds, from -64800 to +64800
 410      * @return the ZoneOffset, not null
 411      * @throws DateTimeException if the offset is not in the required range
 412      */
 413     public static ZoneOffset ofTotalSeconds(int totalSeconds) {
 414         if (Math.abs(totalSeconds) > MAX_SECONDS) {
 415             throw new DateTimeException("Zone offset not in valid range: -18:00 to +18:00");
 416         }
 417         if (totalSeconds % (15 * SECONDS_PER_MINUTE) == 0) {
 418             Integer totalSecs = totalSeconds;
 419             ZoneOffset result = SECONDS_CACHE.get(totalSecs);
 420             if (result == null) {
 421                 result = new ZoneOffset(totalSeconds);
 422                 SECONDS_CACHE.putIfAbsent(totalSecs, result);
 423                 result = SECONDS_CACHE.get(totalSecs);
 424                 ID_CACHE.putIfAbsent(result.getId(), result);
 425             }
 426             return result;
 427         } else {
 428             return new ZoneOffset(totalSeconds);
 429         }
 430     }
 431 
 432     //-----------------------------------------------------------------------
 433     /**
 434      * Constructor.


 679      * @return the adjusted object, not null
 680      * @throws DateTimeException if unable to make the adjustment
 681      * @throws ArithmeticException if numeric overflow occurs
 682      */
 683     @Override
 684     public Temporal adjustInto(Temporal temporal) {
 685         return temporal.with(OFFSET_SECONDS, totalSeconds);
 686     }
 687 
 688     //-----------------------------------------------------------------------
 689     /**
 690      * Compares this offset to another offset in descending order.
 691      * <p>
 692      * The offsets are compared in the order that they occur for the same time
 693      * of day around the world. Thus, an offset of {@code +10:00} comes before an
 694      * offset of {@code +09:00} and so on down to {@code -18:00}.
 695      * <p>
 696      * The comparison is "consistent with equals", as defined by {@link Comparable}.
 697      *
 698      * @param other  the other date to compare to, not null
 699      * @return the comparator value, negative if less, postive if greater
 700      * @throws NullPointerException if {@code other} is null
 701      */
 702     @Override
 703     public int compareTo(ZoneOffset other) {
 704         return other.totalSeconds - totalSeconds;
 705     }
 706 
 707     //-----------------------------------------------------------------------
 708     /**
 709      * Checks if this offset is equal to another offset.
 710      * <p>
 711      * The comparison is based on the amount of the offset in seconds.
 712      * This is equivalent to a comparison by ID.
 713      *
 714      * @param obj  the object to check, null returns false
 715      * @return true if this is equal to the other offset
 716      */
 717     @Override
 718     public boolean equals(Object obj) {
 719         if (this == obj) {
 720            return true;
 721         }
 722         if (obj instanceof ZoneOffset) {
 723             return totalSeconds == ((ZoneOffset) obj).totalSeconds;
 724         }


   1 /*
   2  * Copyright (c) 2012, 2016, Oracle and/or its affiliates. All rights reserved.
   3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
   4  *
   5  * This code is free software; you can redistribute it and/or modify it
   6  * under the terms of the GNU General Public License version 2 only, as
   7  * published by the Free Software Foundation.  Oracle designates this
   8  * particular file as subject to the "Classpath" exception as provided
   9  * by Oracle in the LICENSE file that accompanied this code.
  10  *
  11  * This code is distributed in the hope that it will be useful, but WITHOUT
  12  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  13  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  14  * version 2 for more details (a copy is included in the LICENSE file that
  15  * accompanied this code).
  16  *
  17  * You should have received a copy of the GNU General Public License version
  18  * 2 along with this work; if not, write to the Free Software Foundation,
  19  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  20  *
  21  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  22  * or visit www.oracle.com if you need additional information or have any


 358      * @param minutes  the time-zone offset in minutes, from 0 to &plusmn;59
 359      * @param seconds  the time-zone offset in seconds, from 0 to &plusmn;59
 360      * @throws DateTimeException if the offset is not in the required range
 361      */
 362     private static void validate(int hours, int minutes, int seconds) {
 363         if (hours < -18 || hours > 18) {
 364             throw new DateTimeException("Zone offset hours not in valid range: value " + hours +
 365                     " is not in the range -18 to 18");
 366         }
 367         if (hours > 0) {
 368             if (minutes < 0 || seconds < 0) {
 369                 throw new DateTimeException("Zone offset minutes and seconds must be positive because hours is positive");
 370             }
 371         } else if (hours < 0) {
 372             if (minutes > 0 || seconds > 0) {
 373                 throw new DateTimeException("Zone offset minutes and seconds must be negative because hours is negative");
 374             }
 375         } else if ((minutes > 0 && seconds < 0) || (minutes < 0 && seconds > 0)) {
 376             throw new DateTimeException("Zone offset minutes and seconds must have the same sign");
 377         }
 378         if (minutes < -59 || minutes > 59) {
 379             throw new DateTimeException("Zone offset minutes not in valid range: value " +
 380                     minutes + " is not in the range -59 to 59");
 381         }
 382         if (seconds < -59 || seconds > 59) {
 383             throw new DateTimeException("Zone offset seconds not in valid range: value " +
 384                     seconds + " is not in the range -59 to 59");
 385         }
 386         if (Math.abs(hours) == 18 && (minutes | seconds) != 0) {
 387             throw new DateTimeException("Zone offset not in valid range: -18:00 to +18:00");
 388         }
 389     }
 390 
 391     /**
 392      * Calculates the total offset in seconds.
 393      *
 394      * @param hours  the time-zone offset in hours, from -18 to +18
 395      * @param minutes  the time-zone offset in minutes, from 0 to &plusmn;59, sign matches hours and seconds
 396      * @param seconds  the time-zone offset in seconds, from 0 to &plusmn;59, sign matches hours and minutes
 397      * @return the total in seconds
 398      */
 399     private static int totalSeconds(int hours, int minutes, int seconds) {
 400         return hours * SECONDS_PER_HOUR + minutes * SECONDS_PER_MINUTE + seconds;
 401     }
 402 
 403     //-----------------------------------------------------------------------
 404     /**
 405      * Obtains an instance of {@code ZoneOffset} specifying the total offset in seconds
 406      * <p>
 407      * The offset must be in the range {@code -18:00} to {@code +18:00}, which corresponds to -64800 to +64800.
 408      *
 409      * @param totalSeconds  the total time-zone offset in seconds, from -64800 to +64800
 410      * @return the ZoneOffset, not null
 411      * @throws DateTimeException if the offset is not in the required range
 412      */
 413     public static ZoneOffset ofTotalSeconds(int totalSeconds) {
 414         if (totalSeconds < -MAX_SECONDS || totalSeconds > MAX_SECONDS) {
 415             throw new DateTimeException("Zone offset not in valid range: -18:00 to +18:00");
 416         }
 417         if (totalSeconds % (15 * SECONDS_PER_MINUTE) == 0) {
 418             Integer totalSecs = totalSeconds;
 419             ZoneOffset result = SECONDS_CACHE.get(totalSecs);
 420             if (result == null) {
 421                 result = new ZoneOffset(totalSeconds);
 422                 SECONDS_CACHE.putIfAbsent(totalSecs, result);
 423                 result = SECONDS_CACHE.get(totalSecs);
 424                 ID_CACHE.putIfAbsent(result.getId(), result);
 425             }
 426             return result;
 427         } else {
 428             return new ZoneOffset(totalSeconds);
 429         }
 430     }
 431 
 432     //-----------------------------------------------------------------------
 433     /**
 434      * Constructor.


 679      * @return the adjusted object, not null
 680      * @throws DateTimeException if unable to make the adjustment
 681      * @throws ArithmeticException if numeric overflow occurs
 682      */
 683     @Override
 684     public Temporal adjustInto(Temporal temporal) {
 685         return temporal.with(OFFSET_SECONDS, totalSeconds);
 686     }
 687 
 688     //-----------------------------------------------------------------------
 689     /**
 690      * Compares this offset to another offset in descending order.
 691      * <p>
 692      * The offsets are compared in the order that they occur for the same time
 693      * of day around the world. Thus, an offset of {@code +10:00} comes before an
 694      * offset of {@code +09:00} and so on down to {@code -18:00}.
 695      * <p>
 696      * The comparison is "consistent with equals", as defined by {@link Comparable}.
 697      *
 698      * @param other  the other date to compare to, not null
 699      * @return the comparator value, negative if less, positive if greater
 700      * @throws NullPointerException if {@code other} is null
 701      */
 702     @Override
 703     public int compareTo(ZoneOffset other) {
 704         return Integer.compare(other.totalSeconds, totalSeconds);
 705     }
 706 
 707     //-----------------------------------------------------------------------
 708     /**
 709      * Checks if this offset is equal to another offset.
 710      * <p>
 711      * The comparison is based on the amount of the offset in seconds.
 712      * This is equivalent to a comparison by ID.
 713      *
 714      * @param obj  the object to check, null returns false
 715      * @return true if this is equal to the other offset
 716      */
 717     @Override
 718     public boolean equals(Object obj) {
 719         if (this == obj) {
 720            return true;
 721         }
 722         if (obj instanceof ZoneOffset) {
 723             return totalSeconds == ((ZoneOffset) obj).totalSeconds;
 724         }


< prev index next >