Вычисление общего члена последовательностей и их сумм

В.И. Ракитин

Данная публикация содержит:
— математические основы по теме "Последовательности и ряды";
—алгоритмы решения некоторых типовых задач на рассматриваемую тему и их запись на алгоритмических языках QBasic, Паскаль, Си;
программы для вычисления значений многочленов в заданной точке.

1. Последовательности и способы их задания. Ряды

  Определение 1. Функция, определенная на множестве натуральных чисел, называется последовательностью.

  Последовательность может быть образована элементами любой природы, занумерованными натуральными числами 1, 2, ..., an, ..., и записана в виде {а1, а2, ..., аn, ...}, или {an}, или аn. Будем рассматривать только числовые последовательности, когда каждому значению аргумента n соответствует определенное число. Элемент последовательности an (элемент с номером n) называют общим членом последовательности.

  Последовательность может быть определена:
 
1) формулой для общего члена последовательности an = (n);
  2) рекуррентными соотношениями (от лат. recurrens — возвращающийся). При этом задаются несколько первых членов последовательности и формулы, позволяющие последовательно, шаг за шагом, определить любой член последовательности. Таким образом, заданные последовательности называют еще возвратными последовательностями.
  Например, заданы два первых члена последовательности а1, а2 и уравнение 2-3-4-1.jpg (683 bytes)(an-2, an-1, an) = 0. Тогда, полагая п = 3, можно составить уравнение для а3: 2-3-4-1.jpg (683 bytes)(a1, а2, а3) = 0, из которого найти a3. Далее, полагая п = 4, из уравнения 2-3-4-1.jpg (683 bytes)(a2, a3, a4)= 0 находится а4 и т.д.
  Рекуррентные соотношения называют рекурсивными функциями (от лат. recursio — возвращение), если общий член последовательности явно выражается через предшествующие члены последовательности. В этом случае функции числа п начиная с некоторого номера явно выражаются через предыдущие значения этой же функции.
  В некоторых частных случаях последовательность можно определить как первым, так и вторым способом, т.е. по формуле для общего члена последовательности получить рекурсивную функцию и наоборот.
  Примеры последовательностей, заданных формулой
 
1) an = a0 + d(n-1) или {a0, a0 + d, a0 + 2d, a0+ 3d, ..., а0 + {n - 1)d, ...} — арифметическая прогрессия с разностью d0. В частности, если a0 = 1 и d = 1, имеем an= п — последовательность натуральных чисел {1, 2, 3, 4, ..., n, ...};
  2) an = a0 • qwpe26.jpg (697 bytes) или {a0, a0 q, a0 qwpe2C.jpg (670 bytes), a0 qwpe2A.jpg (671 bytes), ..., a0 qwpe26.jpg (697 bytes)), ...} — геометрическая прогрессия со знаменателем прогрессии qwpe9.jpg (673 bytes)0 и
qwpe9.jpg (673 bytes)1. Например, для a0 = 2 и q = 2 имеем an = 2wpe2D.jpg (668 bytes), т.е. последовательность вида {2, 4, 8, 16, ..., 2wpe2F.jpg (668 bytes), ...};
  3) an = п! последовательность п! читается как "n факториал" (от англ. factor — сомножитель) и определяется так:
  0!= 1, n!=1•2•3• ... •n;
  {1, 2, 6, 24, 120, ..., п!, ...};
  4) an = 1 / (nwpe2C.jpg (670 bytes) + 1) или {1/2, 1/5, 1/10, 1/17, ... ,1/(nwpe2C.jpg (670 bytes)+2), ...}
  Примеры последовательностей, заданных рекуррентными формулами (рекурсивными функциями)
 
5) а1 = a0, an = an-1 + d арифметическая прогрессия с разностью прогрессии d;
 
6) а1 = a0, an = an-1q — геометрическая прогрессия со знаменателем прогрессии q;
 
7) а1 = 1, an = an-1n — последовательность "п факториал";
  8) Если п < 3, то an = 1, в противном случае an = an-1 + an-2. Каждый элемент последовательности, начиная с третьего, равен сумме двух предшествующих. Эту последовательность {1, 1, 2, 3, 5, 8, 13, 21, ...} называют "числами Фибоначчи";
  9) an = ln ( l + ln ( 2 + ln ( 3 + ... + ln ( n - 1 + lnn ) ...) ) ) или та же последовательность, записанная иначе:
an = ln ( ln ( ln (...ln ( lnn+ п - 1 ) + ... + 3) +2) +1).
  Элементы данной последовательности могут быть выражены с помощью другой последовательности bm, представляемой в виде рекуррентных соотношений. Определим последовательность bn, полагая b1 = lnn и bk = ln (bk-1 + n - к + 1), где k = 2, 3,..., n. Элементы последовательности bm представляют собой рекурсивную функцию, аргументом которой является значение той же функции.
  Применяя рекурсии для bn и используя равенство an = bn, вычислим элемент последовательности an:

b1 = ln n;
b2 = ln (b1 + п - 1) = ln ( ln n + n - 1);
b3 = ln (b2 + n - 2) = ln ( ln (ln n + п - 1) + п - 2);
...  ...  ...  ...  ...  ...  ...  ...  ...   ...  ...  ... ;
an = bn = ln (bn-1 + 1) = ln ( ln ( ln ( ... ( ln ( ln n + n - 1 ) + ... ) + 3 ) + 2 ) + 1 ).

  Последовательности в примерах 5—8 определены с помощью рекурсивных функций. Функции числа п, начиная с некоторого номера, явно выражаются через предыдущие значения этой же функции.

2-3-4-1.jpg (683 bytes)(5) (n) = 2-3-4-1.jpg (683 bytes)(5) (n - 1) + d
2-3-4-1.jpg (683 bytes)(6) (n) = 2-3-4-1.jpg (683 bytes)(6) (n - 1) q
2-3-4-1.jpg (683 bytes)(7) (n) = 2-3-4-1.jpg (683 bytes)(7) (n - 1) n
2-3-4-1.jpg (683 bytes)(8) (n) = 2-3-4-1.jpg (683 bytes)(8) (n - 1) + 2-3-4-1.jpg (683 bytes)(8) (n - 2)

  Определение 2. Формальную сумму, составленную из элементов данной последовательности an, называют рядом, а слагаемое с номером п (общий член последовательности) называется общим членом ряда. Ряд записывается в виде
а1 + а2 + а3 + ... + an + ... wpe2.jpg (686 bytes) an
  Можно определить частичные суммы:
S1 = а1, S2 = а1 + а2, S3 = а1 + а2 + а3, — и т.д.
  Последовательность частичных сумм Sn естественно определяется в виде рекуррентных соотношений:
S0 = 0,   Sn = Sn-1 + an   ( n = 1, 2, 3 ... )
или
S1 = а1,   Sn = Sn-1 + an   ( n = 2, 3, 4 ... )

  Замечание. Иногда, определяя ряд, выписывают несколько первых слагаемых ряда с последующим многоточием без формулы для общего члена ряда. Обязательно следует пополнить задачу, заданную в виде "ребуса", составлением либо формулы для общего члена ряда, либо рекуррентного соотношения для него.

  Подобрать формулу для общего члена ряда

10)1/21 + 1/22 + 1/23 + 1/24 + 1/25 + ... ,

11)1 + 1/2 + 12/4 + 123/8 + 1234/16 + ... ,

12)1 + 1/4 + 1/12 + 1/32 + 1/80 + ...

  Подобранные формулы таковы:
wpe3.jpg (1059 bytes),                   wpe6.jpg (1254 bytes),              wpeA.jpg (1130 bytes).

  Представление ряда с использованием аналитического выражения для общего элемента последовательности
1/21 + 1/22 + 1/23 + ... + 1/2•n + ... = wpe13.jpg (983 bytes)1/2•n ;
1 + 1/2 + 12/4 + ... + (n-1)!/2wpe26.jpg (697 bytes) + ... = wpe13.jpg (983 bytes)(n-1)!/2wpe26.jpg (697 bytes) ;
1 + 1/4 + 1/12 + 1/32 + ... + 1/2wpe26.jpg (697 bytes)•n + ... = wpe13.jpg (983 bytes)1/2wpe26.jpg (697 bytes)•n .

  Замечание. При представлении ряда нумерацию слагаемых часто начинают не с единицы, а с нуля. Примеры одинаковых рядов, имеющих различные формы записи из-за изменения стартового значения счетчика:
wpeC.jpg (889 bytes)1/2•n = wpeB.jpg (876 bytes)1/2(k+1),
wpeC.jpg (889 bytes)(n-1)!/2wpe26.jpg (697 bytes) = wpeB.jpg (876 bytes)k!/2wpeD.jpg (694 bytes),
wpeC.jpg (889 bytes)1/2wpe26.jpg (697 bytes)•n = wpeB.jpg (876 bytes)1/2wpeD.jpg (694 bytes)(k+1).

2. Программирование вычислений последовательностей

2.1. Программы без подпрограмм

  Задача 1. С клавиатуры вводятся целые положительные числа п, р и а. Составить программу для вычисления заданного количества членов последовательностей пwpe5.jpg (691 bytes), а^n.jpg (680 bytes), n!. Вывести на экран полученные значения.

  Решение. Будем использовать переменную power (степень) для вычисления степенной функции пwpe5.jpg (691 bytes); переменную exponent (показатель) для вычисления показательной функции а^n.jpg (680 bytes) и переменную factor (множитель) для вычисления факториала п!.
 
Программы состоят из:
  • Блока описаний, где указываются используемые модули, используемые переменные и их типы;
  • Тела программы, включающего;
     — очистку экрана;
     — ввод данных с клавиатуры;
     — вычисление элементов последовательности посредством рекуррентных соотношений, стартовые значения переменных таковы:
          power = 1, exponent = 1, factor = 1,
         формулы для общего члена
         poweri = poweri-11 • п,
         exponenti
= exponenti-11• n,
         factori
= factori-11 • i;
     —
вывод результатов на экран.
  В программах переменные п, р и а — целого типа integer (для неотрицательных целых чисел диапазон их изменения от 0 до 32 767); переменные power, exponent, factor — действительные числа с по крайней мере 6—7 верными знаками после запятой (для положительных чисел в допустимом для типа диапазоне, например от 1,4 • (10-45) до 3,4 • (1038) ). Используемые типы данных имеют названия single, real, float в языках Бейсик, Паскаль, Си соответственно. При выходе какой-либо переменной за пределы диапазона объявленного типа появляется сообщение об ошибке переполнения (overflow).
 
Форматированный вывод результатов работы программ на всех языках программирования одинаков для примера, где п= 10, р=3, а= 3. Имеем: n^p.jpg (691 bytes)= lO^3.jpg (689 bytes)= 1000, а^n.jpg (680 bytes) = 3^10 = 59 049, n! == 10! = 3 628 800.

  Программа на языке QBasic ;

'Блок описаний
DIM a AS INTEGER, i AS INTEGER, n AS INTEGER, p AS INTEGER
DIM power AS SINGLE, exponent AS SINGLE, factor AS SINGLE
'Тело программы: очистка экрана, ввод данных с клавиатуры
CLS
INPUT "Введите число n = ", n
INPUT "Введите степень р = ", р
INPUT "Введите основание показательной функции а = ", а
'вычисление элементов последовательности посредством рекуррентных соотношений
power = 1: exponent = 1: factor = 1
FOR i = 1 ТО р
    power = power * n
NEXT i
FOR i = 1 TO n
    exponent = exponent * a
    factor = factor * i
NEXT i
'вывод результатов на экран
st$ = "power=####.#,
exponent=#####.#,
factor=######.#"
PRINT USING st$; power; exponent; factor

  Замечания к блоку описаний в программе на языке QBasic

  • Если для используемых переменных не указан тип, то по умолчанию им присваивается тип single.
  • Если при определении типов последовательно используются операторы
                                                            DEFINT А, I, Р; DEFSGN E-F, Р,
то переменные, имена которых начинаются с A, I, будут иметь тип integer, а переменные, имена которых начинаются с E—F, Р, будут иметь тип single.
  • Оператор
                                                            DIM a, i, n, p AS INTEGER
не объявляет, что тип integer имеют все четыре переменные. Переменные a, i, n будут иметь тип single, и только переменная р будет иметь тип integer.

  Программа на языке Паскаль

{Блок описаний}
uses crt;
var a, i, n, p : integer;
       power, exponent, factor: real;
{Тело программы}
begin
{очистка экрана, ввод данных с клавиатуры}
    clrscr;
    write ( 'Введите число n = ' ); readln(n);
    write ( 'Введите степень р = ' ); readln(р);
    write ( 'Введите основание показательной функции а = ' ); readln (а);
{вычисление элементов последовательности посредством рекуррентных соотношений}
    power := 1; exponent := 1; factor ;= 1;
    for i := 1 to p do power := power * n;
    for i := 1 to n do
     begin
         exponent := exponent * a;
         factor := factor * i
     end;
         {вывод результатов на экран}
    writeln ( 'power= ', power:1:1,
                   'exponent= ',exponent: 1:1,
                    'factor=', factor:1:1 );
    readln
end.

Программа на языке Си

/* Используемые модули */
#include <conio.h>
#include <stdio.h>
/*0сновная программа включает */
void main ( )
{
/*описание переменных, очистку экрана, ввод данных с клавиатуры */
    int a, i, n, p;
    float power, exponent, factor ;
    clrscr ( ) ;
    printf ("Введите число n = ") ;
    scanf ("%d", &n) ;
    printf ("Введите степень р = ");
    scanf ("%d", &p);
    printf ("Введите основание показательной функции а = "); scanf("%d",&а);
/*вычисление элементов последовательности посредством рекуррентных соотношений */
    power = exponent = factor = 1;
    for (i = 1; i <= p; i++) power *= n;
    for (i = 1; i <= n; i++)
      {
         exponent *= a;
         factor *= i;
      }
/*вывод результатов на экран */
    printf ("power=%l.1f exponent=%l.1f
                  factor=%l.lf \ n",
                  power, exponent, factor) ;
    getch( ) ;
}

2.2. Программы с подпрограммами-функциями

Рассмотрим вновь задачу 1 п. 2.1. Для вычисления значений степенной и показательной функций будем использовать подпрограмму-функцию двух целых положительных переменных power (x, у) , возвращающую значение функции х^y, и подпрограмму-функцию factor (x), возвращающую факториал —  x!. При вычислении элементов последовательности в подпрограммах используются рекуррентные соотношения п. 2.1.

Программа на языке QBasic

DECLARE FUNCTION power! (x AS INTEGER, у AS INTEGER)
DECLARE FUNCTION factor! (x AS INTEGER)
DIM A AS INTEGER, N AS INTEGER, P AS INTEGER
CLS
INPUT "Введите число n = ", n
INPUT "Введите степень p = ", p
INPUT "Введите основание показательной функции а = ", а
st$ = "power=####.#,
exponent = #####.#,
factor=#######.#"
PRINT USING st$; power(n, p) ; power(a, n) ;
factor (n)
'Переменные i и у — локальные, используемые только в подпрограмме
FUNCTION factor! (x-AS INTEGER)
DIM i AS INTEGER, у AS SINGLE
У = 1
FOR i = 1 TO x
   у = у * i
NEXT i
    factor = у
END FUNCTION
'Переменные i и z — локальные, используемые только в подпрограмме
FUNCTION power! (x AS INTEGER, у AS INTEGER)
DIM i AS INTEGER, z AS SINGLE
z = 1
FOR i = 1 TO y
     z = z * x
NEXT i
power = z
END FUNCTION

Программа на языке Паскаль

uses crt;
var a, n, p : integer;
{ Переменные i и у — локальные, используемые только в подпрограмме }
function factor (x : integer) : real;
var i : integer;
       y : real;
begin
      y : =l;
      for i : = 1 to x do у : = у * i;
      factor : = y
end;
{ Переменные i и z — локальные, используемые только в подпрограмме }
function power (x, y : integer) : real;
var i : integer;
       z : real;
begin
      z : = 1;
      for i : =l to y do z := 2 * x;
      power := z
end;
{Основная программа}

begin
    clrscr;
    write ( 'Введите число n = ' ); readln (n);
    write ( 'Введите степень p = ' ); readln (p);
    write ( 'Введите основание показательной функции а = ' ); readln (a);
    writeln ( 'power=', power (n, p) : 1 : 1,
                   'exponent=', power (a, n) : 1 : 1,
                   'factor=', factor (n) : 1 : 1 );
    readln
end.

Программа на языке Си

#include <stdio.h>
#include <conio.h>
/* Переменные i и у — локальные, используемые только в подпрограмме */
float factor (int x)
{
    int i;
float y;
    for (y=l, i = 1; i <= x; i++)  y *= i;
    return (y) ;
}
/* Переменные i и z — локальные, используемые только в подпрограмме */
float power (int x, int y)
{
    int i;
    float z;
    for (z=l, i = 1; i <= y; i++) z *= x;
    return (z) ;
}
/*0сновная программа */
void main( )
{
    int a, n, p;
    clrscr ( ) ;
    printf ("Введите число n = ");
    scanf ("%d", &n);
    printf ("Введите степень р = "); scanf ("%d",&p) ;
    printf ("Введите основание показательной функции а = "); scanf ("%d", &а) ;
    printf ("power=%l. 1f exponent=%l. 1f factor=%l. lf\n",
            power (n, p), power (a, n), factor (n) ) ;
    getch( ) ;
}

2.3. Полпрограммы-функции с рекурсией

  Изменим теперь вид подпрограмм-функций, используя рекурсивный вызов функций. Оформление подпрограмм практически соответствует математическому определению рекурсивной функции: функция вызывает из подпрограммы саму себя с предшествующими значениями аргументов.

  Подпрограммы на языке QBasic

'Подпрограмма-функция factor (х) определена для неотрицательных х
FUNCTION factor! (x AS INTEGER)
   IF х = 0 THEN
      factor = 1
   ELSE
      factor = x*factor (x - 1)
   END IF
END FUNCTION
'Подпрограмма-функция power (x, y) определена для неотрицательных у
FUNCTION power! (x AS INTEGER, у AS INTEGER)
   IF у = 0 THEN
     power =1 ;
   ELSE
     power = x*power (x, у - 1)
   END IF
END FUNCTION

Подпрограммы на языке Паскаль

{ Подпрограмма-функция factor(x) определена для неотрицательных х}
function factor (x : integer) : real;
begin
      if x = 0 then factor :=1
      else factor:=x* factor (x-l)
   end;
{Функция power (x, y) определена для неотрицательных у}
function
power (x, у : integer) : real;
begin
     if у = 0 then power:=1
     else power := x * power (x, y-l)
end;

Подпрограммы на языке Си

/* Подпрограмма-функция factor(x) определена для неотрицательных х */
float factor (int x)
{
    if (x = 0) return(1) ;
    else return (x*factor (x-1) );
}
/* Подпрограмма-функция power(x, y) определена для неотрицательных у*/
float power (int x, int y)
{
    if (y = 0) return(1) ;
    else return (x*power (x, y-1) );
}

  Замечание.
  Рекурсивный вызов функций иногда-существенно замедляет работу программы. В этом можно убедиться, сравнивая работу двух программ, вычисляющих числа Фибоначчи.
  На любом из трех языков программирования проведите вычисления чисел Фибоначчи при п = 5, 10, 20, 30 по двум программам. Программы отличаются тем, что подпрограммы-функции для чисел Фибоначчи fib (x) в одном из вариантов используют рекурсивный вызов функции. Даже очень быстрые компьютеры заметно "задумываются", проводя вычисления по программе с рекурсией при п = 30. Объясняется это тем, что рекурсивная функция для нахождения fib (30) дважды вычисляет fib (28), ... 8 раз fib (25) и т.д.

Программа, вычисляющая числа Фибоначчи, на языке QBasic

DECLARE FUNCTION fib! (x AS INTEGER)
DIM N AS INTEGER
CLS
INPUT "n=", n
PRINT USING "fib (###) = ########"; n; fib (n)

FUNCTION fib! (x AS INTEGER)
DIM i AS INTEGER, DIM y AS SINGLE
DIM fib1 AS SINGLE, fib2 AS SINGLE
    IF x < 3 THEN
        fib = 1
    ELSE
        fib1 = 1: fib2 = 1
        FOR i = 3 TO x
                 y = fib1 + fib2
                 fib1 = fib2
                 fib2 = y
        NEXT i
        fib = y
    END IF
END FUNCTION

Рекурсивная функция

FUNCTION fib! (x AS INTEGER)
    IF x < 3 THEN
         fib =1
    ELSE
         fib = fib (x - 1) + fib (x - 2)
    END IF
END FUNCTION

Программа, вычисляющая числа Фибоначчи, на языке Паскаль

program numbers_of_Fibonacci;
uses crt;
var n : integer;
function fib (x : integer) : real;
var i : integer;
    y, fib1, fib2 : rea1;
  begin
    if x < 3 then
      y :=1
    else
      begin
        fib1:=l; fib2:=l;
        for i:=3 to x do
            begin
                 y:=fib1+fib2;
                 fib1:=fib2;
                 fib2:=y
            end
      end;
    fib:=y
  end;
begin
  clrscr;
    write ( 'n=' ); readln (n) ;
    writeln ( 'fib ( ', n, ' ) =' , fib (n) : 10 : 0) ;
    readln
end.

Рекурсивная функция

function fib (x : integer) : real;
  begin
     if x < 3 then
        fib :=1
     else
        fib:=fib (x - 1) + fib (x - 2)
  end;

Программа, вычисляющая числа Фибоначчи, на языке Си
#include <stdio.h>
#include <conio.h>
float fib (int x)
{
  int i;
  float y, fib1, fib2;
  if (x < 3)
    y=1;
  else ;
  for (fib1 = fib2 = 1, i=3; i <= x; i++)
  { у = fib1+fib2; fib1 = fib2; fib2 = y; }
  return (y) ;
}

void main( )
{
    int n;
    clrscr ( );
    printf ("n = "); scanf ("%d", &n);
    printf ("fib (%d) = %10.0f\n", n, fib (n) ) ;
    getch ( ) ;
}

Рекурсивная функция

float fib (int x)
{
   if (x < 3) return(1) ;
   else return (fib (x-1) + fib (x-2) );
}

2. 4. Последовательность, элементы которой — рекурсивные функции

  Задача 2. Вычислить значение выражения
  аn = ln (1 + ln (2 + ln (3 + ... + ln (n —1 + 4 + Inn) ...) ) ),
где п — некоторое натуральное число, удовлетворяющее условию 5 <= п <= 20, причем это число выбирается случайным образом в самой программе.
  Решение. В подпрограмме-функции а (x) полностью воспроизведен алгоритм примера 9 п.1. В основной программе используется функция, называемая генератором случайных чисел: RND, или random ( ) , в зависимости от языка программирования, и процедура RANDOMIZE. Можно отметить, что натуральный логарифм вычисляется в языках Бейсик и Си библиотечной функцией log, а в языке Паскаль — ln.

Программа на языке QBasic

DECLARE FUNCTION a! (x AS INTEGER)
'Основная программа
DIM n AS INTEGER
CLS
RANDOMIZE TIMER
n = 5 + INT (16 * RND)
PRINT n; " "; a(n)
'Подпрограмма, вычисляющая элемент последовательности а(х)
FUNCTION a! (x AS INTEGER)
DIM k AS INTEGER
DIM b AS SINGLE
   b = LOG (x)
   FOR k = 2 TO x
        b = LOG (b + x - k + 1)
   NEXT k
   a = b
END FUNCTION

Программа на языке Паскаль

uses crt;
var n : integer;
{Подпрограмма, вычисляющая элемент последовательности а(x)}
function a (x : integer) : real;
var k : integer;
       b : real;
  begin
    b := ln(x);
    for k := 2 to x do
        b := ln (b+x-k+l) ;
    a := b
  end;
{Основная программа}
begin
    clrscr;
    randomize;
    n :=5 + random (16);
    writeln (n, ' ', a (n) : 12 : 10);
    readln
end.

Программа на языке Си
#include <stdio.h>
#include <conio.h>
#include <math.h>
#include <stdlib.h>
/* Подпрограмма, вычисляющая элемент последовательности а (х) */
float a (int x)
{ int k;
   float b;
   b = log (x) ;
   for (k=2; k <= x; k++)
      b = log (b+x-k+1) ;
   return (y) ;
}

/*0сновная программа*/
void main( )
{ int n;
   clrscr( ) ;
   randomize( );
   n =5 + random (16);
   printf ("%d %12. 10f\n",n, a (n) ) ;
   getch( ) ;
}
    

3. Программирование вычислений сумм последовательностей

  Задача 3. Пусть задана последовательность

     an=(-1)n+1  ( n • 2n / (2n + 1)! )  ( n = 1, 2, 3, 4, … ).

     Вычислить:
    1. Сумму п слагаемых данной последовательности; число п вводится с клавиатуры.
     2. Сумму нечетных элементов последовательности; номера которых не превосходят n.
    3. Сумму членов данной последовательности при условии, что абсолютная погрешность вычисления не больше 0,0001.  Найти при этом число слагаемых, образующих эту сумму.

  Решение. Обозначим через sum1, sum2 и sum3 переменные для сумм, которые требуется найти в пунктах 1, 2 и 3 поставленной задачи. В программах это будут переменные типа single, real, float (для языков Бейсик, Паскаль, Си).

Вариант 1
 
Представим выражение для общего члена последовательности в виде an= - n • (-2)n / (2n + 1)! .
  Функция для вычисления элементов данной последовательности выражается через функции power и factor.

  На языке QBasic

FUNCTION a# (x AS INTEGER)
а = -x*power (-2, x) / factor (2*x + 1)
END FUNCTION

  На языке Паскаль

function a (x : integer) : real;
begin
  a:= -x*power (-2, x) / factor (2*x+l)
end;

На языке Си

float a (int x)
{return (-x*power (-2, x) / factor (2*x+l ) ) }

Вариант 2

  He представляет труда получить и запрограммировать данную последовательность в виде рекуррентного соотношения.
  Прежде всего по заданной формуле
an = (-1)N+1 ( (n • 2n) / (2n + 1)! )
подставив в нее (n—1) вместо n, получим общий вид для предшествующего члена последовательности
                                                 

  Далее вычислим отношение
                                      
= (-1) [ (n • 2) / ( (n-1) • 2 • n • (2n + 1) ) ] = - 1 / (n - 1) (2n +1),
учитывая, в частности при сокращении, что (2n + 1)! = 1 • 2 • 3 • ... • (2n - l) • 2n • (2n + 1) = (2n - 1)! • 2n • (2n + 1).
  И, наконец, присваивая фактическое значение первому элементу a1 и выражая an через an-1, представляем данную последовательность в рекуррентной форме:

a1 = 1/3, an = an-1• ( -1 / (n-1) (2n+1)   (n = 2, 3 …).

  В соответствий с полученными рекуррентными формулами составлены подпрограммы-функции.

  На языке QBasic

FUNCTION a! (x AS INTEGER)
DIM i AS INTEGER, b AS single
IF x <= 1 THEN
 b = 1 / 3
ELSE
 b = 1 / 3
 FOR j = 2 TO x
   b = -b / ( j - 1 ) / ( 2*j + 1 )
 NEXT j
END IF
 a = b
END FUNCTION

  На языке Паскаль

FUNCTION a ( x : integer ) : real;
var  j : integer;
     b : real;
begin
     if x <= 1 then
        b := 1 / 3
     else
        begin
          b := 1 / 3;
          for j := 2 to x do
          b :=-b/ ( j – 1) / (2*j + 1)
    
end;
  
a := b
end;

На языке Си

float a (int x)
{ int j;

   float b;
   if (x <= 1)

return (1.0 / 3);
   else

   for (b = 1.0 / 3,j = 2;j <= х; j++)

          b*=-l. 0 / (j - 1) / (2*j + 1);
   return (b);
}

Замечания. В языке Си деление 1 / 3 дает целую часть от деления целых чисел, т. е. 0 в данном случае, а деление 1, 0 / 3 возвращает 0,3333333 — верный результат. Выражение —1 / (j - 1) / (2*j + 1) возвращало бы 0, а выражение —1, 0 / (j - 1) / (2*j + 1) дает верный результат.

  Программирование вычисления сумм sum1, sum2 и sum3
  При вычислении сумм последовательностей аn используем рекуррентные соотношения для последовательности частичных сумм в виде.

S0 = 0, si = si-1 + ai (I = 1, 2, 3, … ,n).

Абсолютной погрешностью вычисления называется в данном случае dS = | SnSn-1 | = | аn |. Таким образом, мы будем суммировать элементы ряда до тех пор, пока | аn | > 0,0001. Очередным аn, модуль которого меньше либо равен 0,0001, мы уже пренебрегаем. И тем самым останавливаем процесс суммирования. Программы для решения задачи 3 приведены ниже, следует добавить только подпрограммы-функции а (x) для вычисления элементов последовательности аn (например, вариант 2).

 

Вычисление сумм sum1, sum2, sum3
   На языке QBasic

 'Блок описаний

DECLARE FUNCTION a! (x AS INTEGER)
CONST epsilon - .0001
DIM i AS INTEGER, n AS INTEGER
DIM sum1 AS SINGLE, sum2 AS SINGLE
DIM sum3 AS SINGLE
   'Основная программа
CLS

INPUT "Введите n=", n
sum1=0 : sum2=0 : sum3=0
  'Вычисление sum1 и sum2
FOR i = 1 TO n
      sum1 = sum1 + a ( i )
      IF i MOD 2 = 1 THEN
         sum2 = sum2 + a(  i )
      END IF
NEXT i

  'Вычисление sumЗ и числа слагаемых,
  'образующих сумму
i = 1

DO WHILE ABS ( a ( i ) ) > epsilon
       sum3 = sum3 + a( i )
       i = i + l
LOOP

  'He форматированный вывод результатов
PRINT sum1, sum2, sum3
PRINT i – 1

   'Подпрограмма-функция вычисления для an
FUNCTION a! (x AS INTEGER)

   На языке Паскаль

 {Блок описаний}

 uses crt;
const epsilon = 0.0001;
var i, n : integer;
      sum1, sum2, sum3 : real;

(Подпрограмма-функция для вычисления an}
function a (x : integer) : real;

     

 {Основная программа}
begin
   clrscr;
   write {'Введите n=');
   readln (n);
   sum1:=0; sum2:=0; sum3:=0;

{  {Вычисление sum1 и sum2}
for i := 1 to n do
    begin
         sum1 := sum1 + a (i);
         if i mod 2 = 1 then
          sum2 := sum2 + a (i)
    end;

{Вычисление sum3 и числа слагаемых, образующих сумму}
i := 1;
       while abs (a ( i ) ) > epsilon do
      begin
           sum3 := sum3 + a (i);
           i := i + 1
      end;

{Форматированный вывод результатов}
      writeln ('sum1=',
      suml : 8 : 7, ' sum2=',
      sum2 : 8 : 7, ' sum3=',
      sum3 : 8 : 7,' ', i - l);
      readln
end.

 

  На языке Си

/*Блок описаний*/

#include <stdio.h>
#include <conio.h>
#include <math.h>
#define epsilon 0.0001

/*Подпрограмма-функция для вычисления аn*/

float a (int x)

     

/*0сновная программа*/
void main ( )
{     int i, n;
       float sum1,sum2, sum3;
       clrscr ( ) ;
       printf ("n = ");
       scanf ("%d", &n);

/*Вычисление sum1 и sum2*/
for (sum1 = sum2 =0, i = 1;

   i <=n;  i++)
   {

  
 sum1 +=a (i) ;

    
if (i % 2 == 1)
    
sum2 += a (i) ;

}
/*
Вычисление sum3 и числа слагаемых, образующих сумму*/
for (sum3 = 0, i=l;
 
fabs (a (i) ) >epsilon; i++)
  
sum3 += a (i) ;

 /* Форматированный вывод результатов */

   printf ("sum1 = % 8.7f
   sum2 = % 8.7f
   sum3 = % 8.7f  %d \ n",
   sum1, sum2, sum3, i-1) ;
   getch ( ) ;

}

  Тестирование этой программы при п = 3 дает следующие строки на экране:

Введите n=3

sum1=0. 2714286 sum2=0. 3380952 sum3=0 .2712522   4

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

a1 = 1/3, s1 = а1; ai = ai-1• ( -1 / (i-1) (2i – 1) ),

si = si-1+ ai  (i = 2, 3, ..., n).

  В данном алгоритме

• сначала первому элементу и сумме присваиваются стартовые значения,

• затем по рекуррентной формуле вычисляется следующее слагаемое, которое и добавляется к предыдущему значению суммы;

     • и далее необходимое число повторений вычислений.

Этот алгоритм, например на языке Бейсик, реализуется с помощью цикла со счетчиком FOR ... NEXT

DIM b AS SINGLE

b = 1 / 3 : sum1 = b : sum2 = b
FOR i = 2 TO n
       b = -b / (i - 1) / (2*i + l)
       sum1 = sum1 + b
             IF l MOD 2=1 THEN

            
sum2 = sum2 + b
        END IF
NEXT I

4. Вычисление значения многочлена

Определение 3. Функция вида

                              Pn(x) = a0xn + a1xn-1 + a2xn-2 + … + an-1x + an (a0not=.jpg (689 bytes)0) называется многочленом, или полиномом, n-й степени. Любой многочлен определяется своей степенью и набором коэффициентов {а0, a1, а2, ..., an-1, an }, а для его вычисления необходимо еще задать значение аргумента x.

В языках программирования конечные последовательности реализуются через структуру, называемую массивом, Номер, определяющий конкретный элемент массива, называется индексом. При описании массивов определяются тип элементов массива и диапазон его индексов. По умолчанию элементы массива нумеруются с нуля (в языке Паскаль всегда явное указание диапазона индексов). Массивы естественно использовать в программах для коэффициентов многочлена.

  Задача 4. Составить программу для вычисления значения многочлена в точке х. Степень многочлена n, коэффициенты многочлена
                    и значение x вводятся с клавиатуры.
  Решение. Положим, что переменная а — это массив коэффициентов многочлена, его тип — single, real или float. Элементы этого массива обозначаются — a (i) (для языка Бейсик) или а [i] для Паскаля и Си (i = 0, 1, 2, ..., n).

  При вычислении значения многочлена в заданной точке x используется алгоритм вычисления суммы. Остановимся на двух различных схемах вычисления.

  1-й вариант вычисления значения многочлена

Вначале степенной функции  присваивается значение х0 = 1 , а сумме s — последнее слагаемое аn. Далее последовательно вычисляются значения степенной функции при увеличении на 1 показателя степени и сумма пополняется очередным слагаемым. В целом алгоритм состоит из следующих шагов вычислений:

   Начальные значения: 0 = 1, S0 = аn .

   1-й шаг: 1 = 0x = x, x = x,

                   s1 = s0 + an-11  = an-1x + an.

  2-й шаг: 2 = 1x = x x = x2,

                   s2 = s1 + an-22  = an-1x2 + an-1x + an.
  3-й шаг: 3 = 2 x = x3,

                   s3 = s2 + an-33  = an-3x3 + an-2x2 + an-1x + an.

                   …………………………………………………………..

  n-й шаг: n = n-1x = xn,

                   sn = sn-1 + a0n  = a0xn + a1xn-1 + a2xn-2 + … + an-1x + an.

   Компактная запись алгоритма выглядит так:
                   0 = 1,
s0 = an, i = i-1 x,
                  
s
1 = si-1 +
+ an-1i (i = 1, 2, 3, …, n).
 
 В программах реализация этих вычислений выделена жирным шрифтом

 

      Программы

  На языке Qbasic

 

DIM i AS INTEGER, n AS INTEGER
DIM f AS SINGLE, s AS SINGLE
DIM x AS SINGLE
DIM a (0 TO 10) AS SINGLE
CLS
INPUT "Введите n=", n
INPUT "Введите x=", x
PRINT "Введите "; n + 1;
PRINT " коэффициента многочлена "; n; "степени "

FOR i = 0 ТО n
INPUT "", a (i)
NEXT

f = 1: s = a(n)
FOR i =1 TO n

   f =f*x: s=s + a (n - i) * f
NEXT i
PRINT USING "#####"; s

 На языке Паскаль

 

uses crt;
var i, n : integer;
    
f, s, x : real;

     a : array[0..10] of real;
begin
    
clrscr;

     write ('Введите n=');
    
readln (n);

     write ('Введите х=');
    
readln (x) ;
    
writeln ('Введите ',n+l,

                ' коэффициента многочлена',
               
n,' степени ');
    
for i := 0 to n do
             
readln (a [i] );
    
f := 1; s := a[n];
    
for i := 1 to n do
       
begin

       f:=f*x; s:=s + a [n - i]*f
       
end;

     writeln (s : 9 : 7);
    
readln
end.

 На языке Си

#include <stdio.h>
#include <conio.h>

void main( )
{
int i, n;
float f, s, x, a [10];
clrscr ( );
printf ("Введите n="); scanf ("%d", &n) ;
printf ("Введите x="); scanf ("%f", &x);
printf ("Введите %d коэффициента многочлена %d степени \ n",n+1,n);

for (i=0; i<=n; i++) scanf("%f", &a [i] );
for (f = l, s = a [n], i =1; I <= n; i++)
{
 
f*=x; s+=a [n-i] *f;

}

printf ("%9.7f \ n", s) ;
getch( ) ;

2-й вариант вычисления значения многочлена — схема Горнера

Рекуррентный способ задания многочлена в виде последовательно вычисляемых формул

Р0 = а0, Рi = Рi-1x + аi (i =1, 2, 3, .... n),

называют схемой Горнера.

Эту схему вычислений можно записать одним выражением: Рn = (...( ( a0x + a1)x + а2)x + ... + аn-1)x + аn.

Эти формы записи дают следующие пошаговые вычисления значения многочлена в точке x:

  Схема Горнера

Р0 = a0

p1 = Р0 • x + a1 = a0x + a1

p2 = Р1 • x + a2 = a0x2 + a1x + a2

p3 = Р2 • x + a3 = a0x3 + a1x2 + a2x + a3

…………………………………………………….

pn = Рn-1 • x + an = a0xn + a1xn-1 + a2xn-2 + … + a + a + an-1x + an

 

Ниже приведены фрагменты программы - реализации схемы Горнера.

  На языке QBasic

Р = а (0)

FOR i = 1 ТО n

Р = р * х + a (i)
NEXT i

 На языке Паскаль

 Р := а[0] ;
for i := 1 to n do
   
P := P * x + a [i] ;

   На языке Си

 P = a [0];

     for (i=l; i<=n; i++)
  
P = P * x + a [i] ;

Тестирование программы: пусть вычисляется значение многочлена второй степени Р2(x) = х2 + + 3 при x = - 1 . Значение многочлена равно 2. Результат действия программы представляется на экране так:

Введите n = 2
Введите х = - 1
Введите 3 коэффициента многочлена 2-й степени

1

2

3
2

  Замечание. Схема Горнера позволяет вычислять значение полинома в точке за минимальное количество операций  +, -, *.

                                                                                Литература

     1. Йенсен К., Вирт Н. Паскаль. Руководство для пользователя. М.: Финансы и статистика, 1989.

2. Керниган В., Ритчи Д. Язык программирования Си. М.: Финансы и статистика, 1992,

3. Осипов С.В., Потемкин. В.Г. MS-DOS 5.0. QBasic. M.: Малип, 1992.

     4. Попов В. Б. Турбо Паскаль для школьников. Версия 7.0. ,М.: Финансы и статистика, 1998.

     5. Уэйт М., Прата С, Мартин Д. Язык Си. Руководство для начинающих. М.: Мир, 1988.

 

TopList