View Javadoc
1   ///////////////////////////////////////////////////////////////////////////////////////////////
2   // checkstyle: Checks Java source code and other text files for adherence to a set of rules.
3   // Copyright (C) 2001-2026 the original author or authors.
4   //
5   // This library is free software; you can redistribute it and/or
6   // modify it under the terms of the GNU Lesser General Public
7   // License as published by the Free Software Foundation; either
8   // version 2.1 of the License, or (at your option) any later version.
9   //
10  // This library is distributed in the hope that it will be useful,
11  // but WITHOUT ANY WARRANTY; without even the implied warranty of
12  // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13  // Lesser General Public License for more details.
14  //
15  // You should have received a copy of the GNU Lesser General Public
16  // License along with this library; if not, write to the Free Software
17  // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
18  ///////////////////////////////////////////////////////////////////////////////////////////////
19  
20  package com.puppycrawl.tools.checkstyle.filters;
21  
22  import java.util.Collections;
23  import java.util.HashSet;
24  import java.util.Objects;
25  import java.util.Set;
26  
27  /**
28   * <div>
29   * This filter element is immutable and accepts an integer that matches a CSV value, where
30   * each value is an integer or a range of integers.
31   * </div>
32   */
33  final class CsvFilterElement implements IntFilterElement {
34  
35      /** Filter set. */
36      private final Set<IntFilterElement> filters = new HashSet<>();
37  
38      /**
39       * Constructs a {@code CsvFilterElement} from a CSV, Comma-Separated Values,
40       * string. Each value is an integer, or a range of integers. A range of
41       * integers is of the form integer-integer, such as 1-10.
42       * Note: integers must be non-negative.
43       *
44       * @param pattern the CSV string.
45       * @throws NumberFormatException if a component substring does not
46       *     contain a parsable integer.
47       */
48      /* package */ CsvFilterElement(String pattern) {
49          for (String token : pattern.split(",", -1)) {
50              if (token.isEmpty()) {
51                  continue;
52              }
53              final String trimmedToken = token.trim();
54              final int index = trimmedToken.indexOf('-');
55              if (index == -1) {
56                  final int matchValue = Integer.parseInt(trimmedToken);
57                  addFilter(new IntMatchFilterElement(matchValue));
58              }
59              else {
60                  final int lowerBound =
61                      Integer.parseInt(trimmedToken.substring(0, index));
62                  final int upperBound =
63                      Integer.parseInt(trimmedToken.substring(index + 1));
64                  addFilter(new IntRangeFilterElement(lowerBound, upperBound));
65              }
66          }
67      }
68  
69      /**
70       * Adds a IntFilterElement to the set.
71       *
72       * @param filter the IntFilterElement to add.
73       */
74      private void addFilter(IntFilterElement filter) {
75          filters.add(filter);
76      }
77  
78      /**
79       * Returns the IntFilters of the filter set.
80       *
81       * @return the IntFilters of the filter set.
82       */
83      private Set<IntFilterElement> getFilters() {
84          return Collections.unmodifiableSet(filters);
85      }
86  
87      /**
88       * Determines whether an Integer matches a CSV integer value.
89       *
90       * @param intValue the Integer to check.
91       * @return true if intValue is an Integer that matches a CSV value.
92       */
93      @Override
94      public boolean accept(int intValue) {
95          boolean result = false;
96          for (IntFilterElement filter : getFilters()) {
97              if (filter.accept(intValue)) {
98                  result = true;
99                  break;
100             }
101         }
102         return result;
103     }
104 
105     @Override
106     public boolean equals(Object object) {
107         if (this == object) {
108             return true;
109         }
110         if (object == null || getClass() != object.getClass()) {
111             return false;
112         }
113         final CsvFilterElement csvFilter = (CsvFilterElement) object;
114         return Objects.equals(filters, csvFilter.filters);
115     }
116 
117     @Override
118     public int hashCode() {
119         return Objects.hash(filters);
120     }
121 
122 }