Сумма всех натуральных чисел от 0 до N. Решение (N+1)/2*N

Ответ на мой вопрос:

Сумма всех действительных чисел от 0 до N расчитывается по формуле (N+1)/2*N и никаких циклов и рекурсий!!!

Приведу примеры трёх вариантов решения этой задачи. Комментировать не буду, примеры довольно простые.

Решим эту задачу с помощью цикла:

private static long Cicle(long end)
{
long result = 0;
for(long i=0; i <>
{
result = result + i;
}
return result;
}

И с помощью рекурсии:

private static long Recursion(long end)
{
long result;
if (end==1) return 1;
result = Recursion(end-1)+end;
return result;
}

По формуле:

private static long Formula(long end)
{
return (long)((end + 1) / 2.0 * end);
}


Возможно, в некоторых языках программирования уже есть готовая реализация этой функции. В java не знаю, если есть то киньте каммент, буду тоже знать ;)

Теперь сравним эти три метода.

Расчет по формуле. Явно правильное решение, если знать формулу :-D
Попробуем посчитать время необходимое для расчета суммы чисел до 2-х миллиардов. Для этого воспользуюсь утилитой time:

Solaris# time java -jar /root/sequence_formula.jar 2000000000
Formula says: 2000000001000000000
0.16u 0.11s 0:00.32 84.3%

Понадобилось 00.32 секунды для расчёта.

Рекурсия имеет явный недостаток – очень прожорливая. При конечном значении N около 5000 функция вызывала переполнение стека (Exception in thread "main" java.lang.StackOverflowError). При столь малом значении N трудно судить о скорости выполнения. Рекурсия явно не подходящее решение.

Цикл не требователен к памяти, но прожорлив к вычислительным ресурсам. Проверим, как он считает сумму до 2-х миллиардов:

Solaris# time java -jar /root/sequence_cicle.jar 2000000000
Cicle says: 2000000001000000000
14.33u 0.12s 0:14.55 99.3%

Что и требовалось доказать – целых 14.55 секунды.
Оценка конечна условная, мы не учли время старта самой виртуальной машины Java, некоторые другие важные факты, влияющие на время расчёта, но, тем не менее, этой цифры достаточно, чтобы сделать вывод.

Представляете сколько времени надо, если таких расчётов надо сделать несколько тысяч?!

Вот так вот не зная формул можно нагородить такой костыль, который элементарные вещи будет считать часами или вообще не посчитает ;)

1 комментарий:

  1. public class UsingWhile{
    public static void main(String[] args){
    // Граница суммы, индексные переменные и переменные для записи суммы:
    int count,i=1,j=1,s1=0,s2=0;
    // Считывание границы суммы:
    count=Integer.parseInt(JOptionPane.showInputDialog("Введите границу суммы"));
    // Текстовые переменные:
    String text="Сумма натуральных чисел от 1 до "+count+".\n";
    String str1="Оператор while: ";
    String str2="Оператор do-while: ";
    // Вычисление суммы оператором while:
    while(i<=count){
    s1+=i;
    i++;}
    // Вычисление суммы оператором do-while:
    do{
    s2+=j;
    j++;
    }while(j<=count);
    // Уточнение текста для сообщения:
    str1+=s1+"\n";
    str2+=s2;
    // Вывод окна сообщения на экран:
    JOptionPane.showMessageDialog(null,text+str1+str2);
    }
    }

    ОтветитьУдалить