Статистические расчеты - PullRequest
       1

Статистические расчеты

4 голосов
/ 20 августа 2010

Есть ли какая-нибудь встроенная библиотека, которую я могу использовать для вычисления медианы в java ??

Я работал с apache.commons.math для других статистических функций, но медианы нигде не было найдено.

Спасибо,

Ответы [ 5 ]

9 голосов
/ 20 августа 2010

Поместите все числа в список, отсортируйте список и возьмите среднее значение (или среднее из двух средних значений для четного размера).Нет необходимости в расчетах

7 голосов
/ 20 августа 2010

Какую версию Apache Commmons Math вы используете?Существует средний класс, по крайней мере, начиная с версии 2.1 (более старая версия, я не уверен).Вы можете использовать его как:

Median median = new Median();
median.evaluate(values);
2 голосов
/ 20 августа 2010

Получить значения в объект списка. Давайте предположим, что значения являются целыми числами, а список называется «значения». Тогда

List<Integer> values;
... populate values ...
Collections.sort(values);
int median;
int midpoint=values.size()/2;
if (values.size()%2==1)
  median=values.get(midpoint+1).intValue();
else
  median=(values.get(midpoint).intValue()+values.get(midpoint+1).intValue())/2;

Если количество значений велико, например, в сотнях и более, использование мод-2 может быть технически правильным, но излишним.

Может быть, есть более эффективный способ сделать это - сортировка в большом списке довольно медленная - но это сработает.

О, и вы действительно должны проверить список с нулевыми записями. Может быть, я пропускаю другие граничные условия.

2 голосов
/ 20 августа 2010

Попробуйте объект Медиана .

1 голос
/ 20 августа 2010

Из отдела "слишком много времени у меня на руках": вот небольшой класс MedianGenerator:

/**
 * Methods to calculate the median value of a supplied {@link List}.
 */
public final class MedianGenerator{

    private MedianGenerator(){
    }

    /**
     * Calculate the median of a supplied list.
     * <ol>
     * <li>A copy will be generated</li>
     * <li>this copy will be sorted with the supplied comparator</li>
     * <li>the median will be calculated, using the supplied averageCalculator
     * for collections with an even number of items</li>
     * </ol>
     * 
     * @param data 
     * @param comparator
     * @param averageCalculator
     * @return the median
     */
    public static <T> T calculateMedian(final List<T> data,
        final Comparator<? super T> comparator,
        final AverageCalculator<T> averageCalculator){
        final List<T> copy = new ArrayList<T>(data);
        Collections.sort(copy, comparator);
        return doCalculateMedian(data, averageCalculator);

    }

    /**
     * Calculate the median of a supplied list.
     * <ol>
     * <li>A copy will be generated</li>
     * <li>this copy will be sorted with the supplied comparator</li>
     * <li>the median will be calculated, using the {@link #ALWAYS_FIRST} {@link AverageCalculator}
     * for collections with an even number of items</li>
     * </ol>
     * 
     * @param data 
     * @param comparator
     * @return the median
     */
    @SuppressWarnings("unchecked")
    public static <T> T calculateMedian(final List<T> data,
        final Comparator<? super T> comparator){
        return calculateMedian(data, comparator, (AverageCalculator<T>) ALWAYS_FIRST);
    }

    /**
     * Calculate the median of a supplied list.
     * <ol>
     * <li>A copy will be generated</li>
     * <li>this copy will be sorted using natural ordering</li>
     * <li>the median will be calculated, using the {@link #ALWAYS_FIRST} {@link AverageCalculator}
     * for collections with an even number of items</li>
     * </ol>
     * 
     * @param data 
     * @return the median
     */
    @SuppressWarnings("unchecked")
    public static <T extends Comparable<? super T>> T calculateMedian(final List<T> data){
        return calculateMedian(data, (AverageCalculator<T>) ALWAYS_FIRST);
    }

    /**
     * Calculate the median of a supplied list.
     * <ol>
     * <li>A copy will be generated</li>
     * <li>this copy will be sorted using natural ordering</li>
     * <li>the median will be calculated, using the supplied averageCalculator
     * for collections with an even number of items</li>
     * </ol>
     * 
     * @param data
     * @param averageCalculator 
     * @return the median
     */
    public static <T extends Comparable<? super T>> T calculateMedian(final List<T> data,
        final AverageCalculator<T> averageCalculator){
        final List<T> copy = new ArrayList<T>(data);
        Collections.sort(copy);
        return doCalculateMedian(copy, averageCalculator);
    }

    private static <T> T doCalculateMedian(final List<T> sortedData,
        final AverageCalculator<T> averageCalculator){
        T result;
        if(sortedData.isEmpty()){
            result = null;
        } else{
            final int size = sortedData.size();
            if(size % 2 == 0){
                result =
                    averageCalculator.getAverage(sortedData.get(size / 2 - 1),
                        sortedData.get(size / 2));
            } else{
                result = sortedData.get(size / 2 - 1);
            }

        }
        return result;
    }

    /**
     * Generic accessor method for {@link #ALWAYS_FIRST}.
     */
    @SuppressWarnings("unchecked")
    public static <T> AverageCalculator<T> alwaysFirst(){
        return ALWAYS_FIRST;
    }

    /**
     * {@link AverageCalculator} implementation that always returns the lower
     * bound unchanged.
     */
    @SuppressWarnings("rawtypes")
    public static final AverageCalculator ALWAYS_FIRST =
        new AverageCalculator(){

            @Override
            public Object getAverage(final Object first, final Object second){
                return first;
            }

        };

    /**
     * When there is an even number of items, this interface is used to generate
     * the average between the two middle items.
     */
    public static interface AverageCalculator<E> {

        E getAverage(E first, E second);
    }

}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...