View Javadoc
1   /*
2    * Licensed to the Apache Software Foundation (ASF) under one or more
3    * contributor license agreements.  See the NOTICE file distributed with
4    * this work for additional information regarding copyright ownership.
5    * The ASF licenses this file to You under the Apache License, Version 2.0
6    * (the "License"); you may not use this file except in compliance with
7    * the License.  You may obtain a copy of the License at
8    *
9    *      http://www.apache.org/licenses/LICENSE-2.0
10   *
11   * Unless required by applicable law or agreed to in writing, software
12   * distributed under the License is distributed on an "AS IS" BASIS,
13   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14   * See the License for the specific language governing permissions and
15   * limitations under the License.
16   */
17  package org.apache.commons.collections4.comparators;
18  
19  import java.io.Serializable;
20  import java.util.Comparator;
21  
22  /**
23   * A {@link Comparator} for {@link Boolean} objects that can sort either
24   * true or false first.
25   *
26   * @see #getTrueFirstComparator()
27   * @see #getFalseFirstComparator()
28   * @see #booleanComparator(boolean)
29   *
30   * @since 3.0
31   */
32  public final class BooleanComparator implements Comparator<Boolean>, Serializable {
33  
34      /** Serialization version. */
35      private static final long serialVersionUID = 1830042991606340609L;
36  
37      /** Constant "true first" reference. */
38      private static final BooleanComparator TRUE_FIRST = new BooleanComparator(true);
39  
40      /** Constant "false first" reference. */
41      private static final BooleanComparator FALSE_FIRST = new BooleanComparator(false);
42  
43      /**
44       * Returns a BooleanComparator instance that sorts
45       * {@code <i>trueFirst</i>} values before
46       * {@code &#x21;<i>trueFirst</i>} values.
47       * <p>
48       * Clients are encouraged to use the value returned from
49       * this method instead of constructing a new instance
50       * to reduce allocation and garbage collection overhead when
51       * multiple BooleanComparators may be used in the same
52       * virtual machine.
53       * </p>
54       *
55       * @param trueFirst when {@code true}, sort
56       * {@code true} {@code Boolean}s before {@code false}
57       * @return a singleton BooleanComparator instance
58       * @since 4.0
59       */
60      public static BooleanComparator booleanComparator(final boolean trueFirst) {
61          return trueFirst ? TRUE_FIRST : FALSE_FIRST;
62      }
63  
64      /**
65       * Returns a BooleanComparator instance that sorts
66       * {@code false} values before {@code true} values.
67       * <p>
68       * Clients are encouraged to use the value returned from
69       * this method instead of constructing a new instance
70       * to reduce allocation and garbage collection overhead when
71       * multiple BooleanComparators may be used in the same
72       * virtual machine.
73       * </p>
74       *
75       * @return the false first singleton BooleanComparator
76       */
77      public static BooleanComparator getFalseFirstComparator() {
78          return FALSE_FIRST;
79      }
80  
81      /**
82       * Returns a BooleanComparator instance that sorts
83       * {@code true} values before {@code false} values.
84       * <p>
85       * Clients are encouraged to use the value returned from
86       * this method instead of constructing a new instance
87       * to reduce allocation and garbage collection overhead when
88       * multiple BooleanComparators may be used in the same
89       * virtual machine.
90       * </p>
91       *
92       * @return the true first singleton BooleanComparator
93       */
94      public static BooleanComparator getTrueFirstComparator() {
95          return TRUE_FIRST;
96      }
97  
98      /** {@code true} iff {@code true} values sort before {@code false} values. */
99      private final boolean trueFirst;
100 
101     /**
102      * Creates a {@code BooleanComparator} that sorts
103      * {@code false} values before {@code true} values.
104      * <p>
105      * Equivalent to {@link #BooleanComparator(boolean) BooleanComparator(false)}.
106      * <p>
107      * Please use the static factory instead whenever possible.
108      */
109     public BooleanComparator() {
110         this(false);
111     }
112 
113     /**
114      * Creates a {@code BooleanComparator} that sorts
115      * {@code <i>trueFirst</i>} values before
116      * {@code &#x21;<i>trueFirst</i>} values.
117      * <p>
118      * Please use the static factories instead whenever possible.
119      *
120      * @param trueFirst when {@code true}, sort
121      *  {@code true} boolean values before {@code false}
122      */
123     public BooleanComparator(final boolean trueFirst) {
124         this.trueFirst = trueFirst;
125     }
126 
127     /**
128      * Compares two non-{@code null} {@code Boolean} objects
129      * according to the value of {@link #sortsTrueFirst()}.
130      *
131      * @param b1  the first boolean to compare
132      * @param b2  the second boolean to compare
133      * @return negative if obj1 is less, positive if greater, zero if equal
134      * @throws NullPointerException when either argument {@code null}
135      */
136     @Override
137     public int compare(final Boolean b1, final Boolean b2) {
138         final boolean v1 = b1.booleanValue();
139         final boolean v2 = b2.booleanValue();
140 
141         return v1 ^ v2 ? v1 ^ trueFirst ? 1 : -1 : 0;
142     }
143 
144     /**
145      * Returns {@code true} iff <i>that</i> Object is
146      * a {@link Comparator} whose ordering is known to be
147      * equivalent to mine.
148      * <p>
149      * This implementation returns {@code true}
150      * iff {@code <i>that</i>} is a {@link BooleanComparator}
151      * whose value of {@link #sortsTrueFirst()} is equal to mine.
152      *
153      * @param object  the object to compare to
154      * @return true if equal
155      */
156     @Override
157     public boolean equals(final Object object) {
158         return this == object ||
159                object instanceof BooleanComparator &&
160                 this.trueFirst == ((BooleanComparator) object).trueFirst;
161     }
162 
163     /**
164      * Implement a hash code for this comparator that is consistent with
165      * {@link #equals(Object) equals}.
166      *
167      * @return a hash code for this comparator.
168      */
169     @Override
170     public int hashCode() {
171         final int hash = "BooleanComparator".hashCode();
172         return trueFirst ? -1 * hash : hash;
173     }
174 
175     /**
176      * Returns {@code true} iff
177      * I sort {@code true} values before
178      * {@code false} values.  In other words,
179      * returns {@code true} iff
180      * {@link #compare(Boolean,Boolean) compare(Boolean.FALSE,Boolean.TRUE)}
181      * returns a positive value.
182      *
183      * @return the trueFirst flag
184      */
185     public boolean sortsTrueFirst() {
186         return trueFirst;
187     }
188 
189 }