2012-04-27 3 views
1

Есть ли способ вычисления среднего/минимального/максимального числа всех чисел без использования массива? Необходимо вычислить до 10 000 номеров в секунду.Расчет минимального, максимального и среднего числа введенных номеров

+1

Пожалуйста, добавьте тег домашней работы, если это необходимо. – thb

+0

Я вижу ряд решений, в которых упоминается общая сумма всех чисел. Может ли это вызвать переполнение? –

+0

@ColinD: Чтобы получить среднее значение для серии, вы должны добавить ее в какой-то момент. –

ответ

2

Да,

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

Сделайте противоположное с максимальной переменной.

Добавьте все числа и разделите эту сумму на общее количество, чтобы получить среднее значение.

Следующий код не делает ограничивающей проверки (например, число> 0, общее не переполнение), но должно дать вам идею:

int minimum = // Initialize to large #, in C# would be int.MaxValue 
int maximum = // Initialize to most negative #, in C# would be int.MinValue 
int count = 0; 
int total = 0; 

void StatsForNewNumber(int number) 
{ 
    if (number < minimum) minimum = number; 
    if (number > maximum) maximum = number; 
    count++; 
    total += number; 
} 

int Average() 
{ 
    return total/count; 
} 
+2

как насчет переполнения всего? –

+3

У вас будет такая же проблема с математикой с массивом. Проверьте наличие переполнений, если это возможно для данных вариантов использования. Используйте длинную или даже библиотеку, которая может управлять произвольно большими целыми числами, если это необходимо. Сумма также может быть выполнена в два раза, если приемлемые проблемы с удвоениями приемлемы. –

+0

'long long' теперь стандартно, и почти у каждого его компилятора есть. Используйте это. –

2

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

Boost Accumulators включает в себя реализации всего вышеперечисленного, плюс немало других.

+1

Как насчет переполнения всего? –

+0

@ColinD: В значительной степени, как вы бы использовали массив, а это значит, что это зависит. Вы можете игнорировать его или использовать более крупный тип. Есть и другие способы, но нет особых оснований полагать, что они, в частности, могут применяться здесь. Я полагаю, что связанная библиотека Accumulators имеет код для устранения/предотвращения переполнения (но не помню точно). –

1

Абсолютно: все, что можно вычислить один пункт в то время, ,

Сохраните текущий минимум и текущий максимум, вычислите общее количество и счетчик. Когда вам нужно среднее значение, разделите общее количество на счет, и вы получите ответ.

class calc { 
    double minVal, maxVal, total; 
    int count; 
public: 
    calc() 
    : minVal(numeric_limits<double>::max) 
    , maxVal(numeric_limits<double>::min) 
    , total(0) 
    , count(0) { 
    } 
    void process(double num) { 
     minVal = min(minVal, num); 
     maxVal = max(maxVal, num); 
     total += num; 
     count++; 
    } 
    double getAvg() { 
     // TODO: Check count to be > 0 here 
     return total/count; 
    } 
    double getMin() { 
     return minVal; 
    } 
    double getMax() { 
     return maxVal; 
    } 
} 
+1

как насчет переполнения всего? –

+1

@ColinD Учитывая, что OP запрашивает решение, которое заменяет основанное на массиве, оно не похоже на переполнение общего числа. – dasblinkenlight

1

Создайте четыре переменные: один для хранения MINVAL, один для MAXVAL, один на общую сумму, и один для приращения после каждого нового ввода. сравнивайте каждый новый вход с minVal и maxVal и обновляйте по мере необходимости. Добавьте входное значение к общей сумме, увеличивайте счетчик. Среднее значение всегда является общей суммой/счетчиком, поэтому вы можете запросить это значение на лету, если вам нужно или просто вычислить его в конце, когда закончите.

+0

Он работает с большим количеством ценностей. Что происходит, когда общее количество переполнений? –

+0

@ColinD: просто используйте int64_t (или длинный) для хранения всего и прочитайте ввод в ints, duh. – SigTerm

1

Вам не нужно хранить любые числа в массиве найти среднее/мин/макс, так как вы перебором номеров вы делаете

if(currentSmallest > currentNumber) 
    currentSmallest = currentNumber 

if(currentLargest < currentNumber) 
    currentLargest = currentNumber 

и кроме того, вы будете держать счетчик и общая сумма, и, разделив эти числа, вы получите среднее значение. Не нужно хранить их в массиве.

+0

Как насчет переполнения всего? –

Смежные вопросы