Как я могу представить диапазон в Java?

Скажем, целое число должно быть в пределах диапазона: [0...2147483647]

Я хочу проверить, попадает ли целочисленная переменная в этот диапазон. Я знаю, что это может быть выполнено с помощью простого оператора if-else, но есть ли более эффективный способ проверить, находится ли он в пределах диапазона?

Я бы предпочел не делать этого:

 if (foo >= 0 && foo <= 2147483647) { // do something } 

Apache Commons Lang имеет class Range для выполнения произвольных диапазонов.

 Range test = Range.between(1, 3); System.out.println(test.contains(2)); System.out.println(test.contains(4)); 

У Guava Range есть аналогичный API.

Если вы просто хотите проверить, соответствует ли число длинному значению или значению int, вы можете попробовать использовать его через BigDecimal . Существуют методы longValueExact и intValueExact которые longValueExact исключения, если значение слишком велико для этих исправлений.

Вы можете создать class для представления этого

 public class Range { private int low; private int high; public Range(int low, int high){ this.low = low; this.high = high; } public boolean contains(int number){ return (number >= low && number <= high); } } 

Использование образца:

 Range range = new Range(0, 2147483647); if (range.contains(foo)) { //do something } 

Если вы проверяете множество интервалов, я предлагаю использовать дерево интервалов .

Я знаю, что это довольно старый вопрос, но с streamами Java 8 вы можете получить целый ряд таких функций:

 // gives an IntStream of integers from 0 through Integer.MAX_VALUE IntStream.rangeClosed(0, Integer.MAX_VALUE); 

Тогда вы можете сделать что-то вроде этого:

 if (IntStream.rangeClosed(0, Integer.MAX_VALUE).matchAny(n -> n == A)) { // do something } else { // do something else } 

Вы можете использовать java.time.temporal.ValueRange который принимает long и также будет работать с int :

 int a = 2147; //Use java 8 java.time.temporal.ValueRange. The range defined //is inclusive of both min and max ValueRange range = ValueRange.of(0, 2147483647); if(range.isValidValue(a)) { System.out.println("in range"); }else { System.out.println("not in range"); } 

Вы будете иметь if-check независимо от того, насколько эффективно вы пытаетесь оптимизировать это не столь интенсивное вычисление. Вы можете вычесть верхнюю границу от числа, и если это положительно, вы знаете, что вы находитесь за пределами допустимого диапазона. Возможно, вы можете выполнить некоторую логическую логику бит-сдвига, чтобы понять ее, и вы даже можете использовать теорему Ферма, если хотите (шутите 🙂 Но дело в том, «почему» вам нужно оптимизировать это сравнение? В чем цель?

Для диапазона Comparable я использую следующее:

 public class Range> { /** * Include start, end in {@link Range} */ public enum Inclusive {START,END,BOTH,NONE } /** * {@link Range} start and end values */ private T start, end; private Inclusive inclusive; /** * Create a range with {@link Inclusive#START} * @param start *
Not null safe * @param end *
Not null safe */ public Range(T start, T end) { this(start, end, null); } /** * @param start *
Not null safe * @param end *
Not null safe *@param inclusive *
If null {@link Inclusive#START} used */ public Range(T start, T end, Inclusive inclusive) { if((start == null) || (end == null)) { throw new NullPointerException("Invalid null start / end value"); } setInclusive(inclusive); if( isBigger(start, end) ) { this.start = end; this.end = start; }else { this.start = start; this.end = end; } } /** * Convenience method */ public boolean isBigger(T t1, T t2) { return t1.compareTo(t2) > 0; } /** * Convenience method */ public boolean isSmaller(T t1, T t2) { return t1.compareTo(t2) < 0; } /** * Check if this {@link Range} contains t *@param t *
Not null safe *@return *false for any value of t, if this.start equals this.end */ public boolean contains(T t) { return contains(t, inclusive); } /** * Check if this {@link Range} contains t *@param t *
Not null safe *@param inclusive *
If null {@link Range#inclusive} used *@return *false for any value of t, if this.start equals this.end */ public boolean contains(T t, Inclusive inclusive) { if(t == null) { throw new NullPointerException("Invalid null value"); } inclusive = (inclusive == null) ? this.inclusive : inclusive; switch (inclusive) { case NONE: return ( isBigger(t, start) && isSmaller(t, end) ); case BOTH: return ( ! isBigger(start, t) && ! isBigger(t, end) ) ; case START: default: return ( ! isBigger(start, t) && isBigger(end, t) ) ; case END: return ( isBigger(t, start) && ! isBigger(t, end) ) ; } } /** * Check if this {@link Range} contains other range * @return * false for any value of range, if this.start equals this.end */ public boolean contains(Range
range) { return contains(range.start) && contains(range.end); } /** * Check if this {@link Range} intersects with other range * @return * false for any value of range, if this.start equals this.end */ public boolean intersects(Range range) { return contains(range.start) || contains(range.end); } /** * Get {@link #start} */ public T getStart() { return start; } /** * Set {@link #start} *
Not null safe *
If start > end they are switched */ public Range
setStart(T start) { if(start.compareTo(end)>0) { this.start = end; this.end = start; }else { this.start = start; } return this; } /** * Get {@link #end} */ public T getEnd() { return end; } /** * Set {@link #end} *
Not null safe *
If start > end they are switched */ public Range
setEnd(T end) { if(start.compareTo(end)>0) { this.end = start; this.start = end; }else { this.end = end; } return this; } /** * Get {@link #inclusive} */ public Inclusive getInclusive() { return inclusive; } /** * Set {@link #inclusive} * @param inclusive *
If null {@link Inclusive#START} used */ public Range
setInclusive(Inclusive inclusive) { this.inclusive = (inclusive == null) ? Inclusive.START : inclusive; return this; } }

(Это несколько короткая версия. Полный код доступен здесь )

В Java 8 вы можете сделать следующее:

  import java.util.stream.IntStream; IntStream range = IntStream.rangeClosed(5,10); // simple example if it contains 4 range.anyMatch(x -> x == 4); // check if it contains multiples of 2 etc range.anyMatch(x -> x % 2 == 0); 

Важным отличием является то, что он выделит пространство, необходимое для диапазона. Если вам не нужно это поведение, используйте java.time.temporal.ValueRange, который выделяет пространство только для значения min и max.

  • Android ClassNotFoundException: не нашел class на пути
  • Firebase DatabaseException: Не удалось преобразовать значение типа java.lang.Long в String
  • Точка входа для приложений Java: main (), init () или run ()?
  • Завершить все предыдущие действия
  • XML-документ для строки?
  • Ошибка MediaPlayer -38,0
  • Как вернуть несколько значений?
  • Использование пользовательского шрифта в android TextView с помощью xml
  • Изменение языка ввода клавиатуры Programmatically
  • Как я могу сделать ячейку в ListView в Android расширяться и сокращаться вертикально, когда ее касаются?
  • завершение программы на выходе основного streamа?
  • Interesting Posts

    Использование mod rewrite для изменения URL с переменной имени пользователя

    Почему ему не удалось загрузить атрибут манифеста основного classа из JAR-файла?

    Найти () vs. Where (). FirstOrDefault ()

    Binary Blob усечен до 8000 байт – SQL Server 2008 / varbinary (max)

    Как отобразить все методы объекта?

    Примитив или shell для первичных ключей спящего режима

    Угловая форма: добавление полей формы динамически при нажатии на пользователя

    Windows: копировать / перемещать файлы с регулярными выражениями имен файлов?

    npm ошибки установки с ошибкой: ENOENT, chmod

    Почему отлаженная программа так сильно замедляется при использовании отладки ввода метода?

    Mikrotik – сбросить счетчик пользовательского менеджера после дня или недели

    Преобразование объекта в строку JSON

    Получить внешний HTML-код выбранного элемента

    Созданные iTextSharp PDF-файлы теперь вызывают диалог сохранения в Adobe Reader X

    Целочисленная арифметика в Java с символом char и integer literal

    Давайте будем гением компьютера.