Ситкин. Информатика. Программирование в DELPHI
.pdfРеализуем разработанный алгоритм в проекте. Для ввода значений a, b и h вынесем на форму три компонента Edit, а для пояснений к ним три Label. Для вывода результатов разместим на форме четвёр-
тый компонент Label, для которого следует установить значение True свойства AutoSize (автоподбор размера по содержимому), т.к. заранее неизвестно, сколько значений будет выведено в компонент, поскольку это будет определяться введёнными пользователем размерами диапазона и шага. Расчёт и вывод значений свяжем с событием Button1Click.
procedure TForm1.Button1Click(Sender: TObject); var a, b, h, x, y:real;
begin a:=StrToFloat(Edit1.Text);
b:=StrToFloat(Edit2.Text);
h:=StrToFloat(Edit3.Text);
x:=a; //начальное значение х
while x<=b do
begin //начало тела цикла
if x<=0 then y:=sqr(x) else y:=x; Рис. 7.3
Label4.Caption:= Label4.Caption + #13 +
+ 'x=' + FloatToStr(x) + #9 + 'y=' + FloatToStr(y);
вывод в Label значений предыдущей итерации + перевод строки и добавление значений х и y текущей итерации, т.е. накопление таблицы с каждой итерацией
x:=x+h; //увеличение значения х на шаг end; //конец тела цикла
end; //конец процедуры
В случае ввода пользователем h 0 или a b цикл не сможет за-
вершиться произойдёт «зацикливание», что нужно предотвратить.
81
Оператор цикла с параметром (со счётчиком)
Счётный оператор цикла используется в случаях, когда число
повторений известно заранее. Он имеет вид
for i:=a1 to a2 do оператор S
где for, to, do служебные слова; i параметр (счётчик); a1 и a2
начальное и конечное значение счётчика; оператор S тело цикла.
Счётчик последовательно принимает значения от a1 до a2 с шагом плюс один, причём a1 должно быть меньше или равно a2. Реализуемая схема представлена на рис. 7.4 а.
Возможен другой вид счётного оператора
for i:=a1 downto a2 do оператор S
здесь счётчик последовательно принимает значения от a1 до a2 с ша-
гом минус один, причём a1 |
должно быть больше или равно a2. Реали- |
||||||||
зуемая схема представлена на рис. 7.4 б. |
|
|
|
|
|
||||
|
В обоих случаях значения i, a1 и a2 |
должны быть порядкового |
|||||||
типа. Оператор S выполняется один раз для каждого значения i. |
|||||||||
|
|
|
|
|
|
|
|
|
|
|
i = a1 |
|
i = a1 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
нет |
|
|
нет |
|
нет |
|
|
|
||
|
|
|
|
i = a1 |
.. a2 |
||||
|
i a2 |
i a2 |
|
|
|||||
|
да |
да |
|
|
да |
|
|
||
|
оператор S |
|
оператор S |
|
|
|
оператор S |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
i = i + 1 |
|
i = i 1 |
|
|
|
а |
б |
в |
|
||
|
Рис. 7.4 |
|
82
Иногда работу счётного оператора любого вида на схеме изоб- |
|||||||||||
ражают упрощённо (рис. 7.4 в). |
|
|
|
|
|
|
|||||
Пример 7.2 |
|
|
|
|
|
|
|
|
|
|
|
Разработаем алгоритм и проект для вычисления суммы |
|||||||||||
10 |
|
ln(kx) |
|
ln(2x) |
|
ln(3x) |
|
ln(10x) |
|
||
S |
k |
2 |
|
ln x |
4 |
|
9 |
... |
100 |
. |
|
k 1 |
|
|
|
|
|
|
|||||
начало |
|
|
|
|
Формула для вычисления k-го слагаемого |
||||||
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
данной суммы ak |
ln(kx) . Блок-схема предлага- |
||||||
n = 10 |
|
|
|
|
|
|
|
k 2 |
|
|
|
ввод x |
|
|
|
емого алгоритма представлена на рис. 7.5. |
|||||||
|
|
|
|
||||||||
|
|
|
|
Верхний предел суммирования задан как кон- |
|||||||
S = 0; k = 1 |
|
|
|
станта n=10. После ввода x задаются начальные |
|||||||
|
|
|
|
||||||||
|
нет |
|
значения суммы S=0 и номера слагаемого k=1, |
||||||||
k n |
|
|
|
|
|
|
|
|
|
||
|
|
|
которое в ходе циклического процесса должно |
||||||||
|
|
|
|
||||||||
да |
|
|
|
изменяться в диапазоне 1..n. В теле цикла для |
|||||||
|
|
|
|
||||||||
a=ln(k·x)/k2 |
|
|
|
каждого из них вычисляется значение текущего |
|||||||
|
|
|
|
(k-го) слагаемого, которое прибавляется к |
|||||||
S = S + a |
|
|
|
накапливаемой в цикле частичной сумме S. При |
|||||||
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
этом значения a и S предыдущей итерации «за- |
|||||||
k = k + 1 |
|
|
|
тираются». После этого, увеличив k на единицу, |
|||||||
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
переходим к номеру следующего слагаемого, |
|||||||
|
|
|
|
возвращаемся к началу цикла, проверяя, не пре- |
|||||||
|
|
|
|
высил ли номер слагаемого число n. Если не |
|||||||
вывод S |
|
|
|
превысил, то циклический процесс продолжает- |
|||||||
|
|
|
|
||||||||
конец |
|
|
|
ся, в противном случае он заканчивается, и вы- |
|||||||
|
|
|
водится итоговая сумма n слагаемых. |
|
|||||||
Рис. 7.5 |
|
|
|
|
|||||||
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
83 |
|
|
|
|
|
Число повторений известно заранее, и с каждой итерацией зна-
чение k надо увеличивать на единицу используем оператор for.
procedure TForm1.Button1Click(Sender: TObject);
const n=10;
var a, x, S:real;
k:byte; //счётчик счётного оператора цикла, должен быть целого типа
begin
x:=StrToFloat(Edit1.Text); //при x 0 ошибка выполнения
S:=0; //нач. знач. суммы, чтобы было к чему прибавлять на первой итерации for k:=1 to n do //нач. (и конеч.) знач. номера слагаемого устанавл-ся в for
begin //начало тела цикла
a:=ln(x*k)/sqr(k); //вычисление текущего слагаемого на k-ой итерации
S:=S+a; //добавление слагаемого k-ой итерации к накапливаемой сумме end; //конец тела цикла; оператор for сам увеличит k на единицу
Label2.Caption:='S='+FloatToStr(S); //вывод накопленной суммы
end; //конец процедуры
Пример 7.3
Разработаем алгоритм и проект для вычисления суммы
10 |
xk |
|
|
|
x |
|
|
x2 |
|
|
x3 |
|
|
x10 |
|
||||
S |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
... |
|
|
|
. |
(sin(2x)) |
k 1 |
sin |
2 |
(2x) |
sin |
3 |
(2x) |
sin |
4 |
(2x) |
sin |
11 |
(2x) |
||||||
k 1 |
|
|
|
|
|
|
|
|
|
|
Формула для вычисления k-го слагаемого данной суммы имеет вид
ak |
xk |
|
, в принципе возможен алгоритм, идентичный реше- |
(sin(2x)) |
k 1 |
||
|
|
|
нию предыдущей задачи. Однако в данном случае рациональнее ис-
пользовать для расчёта k-го слагаемого рекуррентное соотношение,
связывающее текущее слагаемое с предыдущим
84
|
a |
|
|
|
xk |
|
|
xk 1 |
|
xk (sin(2x))k |
|
|
x |
|
|||
|
|
k |
|
|
: |
|
|
|
|
, |
|||||||
|
a |
|
|
(sin(2x))k 1 |
(sin(2x))k |
xk 1 (sin(2x))k 1 |
sin(2x) |
||||||||||
|
|
k 1 |
|
|
|
|
|
|
|
|
|
|
|
|
|||
откуда ak |
ak 1 |
x |
. |
Таким образом каждое |
слагаемое |
суммы, |
|||||||||||
|
|||||||||||||||||
sin(2x) |
|||||||||||||||||
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
начиная со второго, определяется через предыдущее, домноженное на рекуррентное соотношение. Такой способ поз-
воляет избежать вычисления больших степеней на каждой старшей итерации. Но этот способ не всегда рационален, так в предыдущей задаче он только усложнит вычисления.
Первое слагаемое вычислим по формуле
S = a; k = 2 |
|
|
a1 |
|
x |
|
; S1 = a1 эти значения (они соот- |
||
|
|
|
|
|
|
||||
|
|
sin |
2 |
(2x) |
|||||
|
|
|
|
|
|
||||
|
|
|
ветствуют k=1) нужно будет задать до входа в |
||||||
k n |
нет |
||||||||
|
|
|
|
|
|
||||
|
|
цикл для начала счёта по ним. Номер слагаемого |
|||||||
|
|
||||||||
|
|
|
|||||||
да |
|
|
k в ходе циклического процесса должен изме- |
||||||
|
|
|
|||||||
a= ax/sin(2x) |
|
|
|||||||
|
|
няться в диапазоне 2..n. С двух, т.к. для k=1 зна- |
|||||||
|
|
|
|||||||
|
|
|
чения слагаемого a и суммы S будут определены |
||||||
|
|
|
|||||||
S = S + a |
|
|
уже до входа в цикл. В теле цикла будет опреде- |
||||||
|
|
|
ляться текущее слагаемое через слагаемое, вы- |
||||||
|
|
|
|||||||
|
|
|
численное на предыдущей итерации, «затирая» |
||||||
k = k + 1 |
|
|
|||||||
|
|
|
|
|
|
|
|
||
|
|
|
его, и добавляться к сумме, найденной также на |
||||||
|
|
|
предыдущей итерации, получая новое, текущее, |
||||||
вывод S |
|
|
значение суммы. Затем осуществляется переход |
||||||
|
|
|
|
|
|
|
|
||
|
|
|
к следующему номеру слагаемого. Когда k пре- |
||||||
конец |
|
|
высит |
n, |
цикл завершится, будет выведена |
||||
|
|
|
|
|
|
|
|
накопленная сумма (рис. 7.6).
Рис. 7.6
85
procedure TForm1.Button1Click(Sender: TObject);
const n=10;
var a, x, S:real;
k:byte; //счётчик счётного оператора цикла, должен быть целого типа |
||
begin |
|
|
x:=StrToFloat(Edit1.Text); //при x = 0 будет ошибка выполнения |
||
a:=x/sqr(sin(2*x)); S:=a; //вычисление начальных значений до тела цикла |
||
for k:=2 to n do |
//нач. (и конеч.) знач. номера слагаемого устанавл-ся в for |
|
begin //начало тела цикла |
||
a:=a*x/sin(2*x); //выч-е тек-го слаг. через самого себя предыдущ. итерации |
||
S:=S+a; //добавление слагаемого k-ой итерации к накапливаемой сумме |
||
end; //конец тела цикла; оператор for сам увеличит k на единицу |
||
Label2.Caption:='S='+FloatToStr(S); //вывод накопленной суммы |
||
end; //конец процедуры |
||
|
Оператор цикла с последующим условием |
|
|
Этот оператор обычно используется когда число повторений за- |
|
ранее не известно, а определяется в ходе циклического процесса |
||
|
|
repeat оператор S until условие |
здесь repeat, until служебные слова; оператор S тело цикла; |
||
|
|
условие переменная или выражение логиче- |
|
|
ского типа. Блок-схема алгоритма, реализуемого |
|
оператор S |
оператором цикла с постусловием, представлена |
|
|
|
|
|
на рис. 7.7. Оператор S выполняется до тех пор, |
нет |
условие |
пока условие впервые не примет значение True. |
|
||
|
|
|
|
да |
Оператор S выполняется как минимум один раз. |
|
Рис. 7.7 |
|
|
|
86 |
Пример 7.4
Разработаем алгоритм и проект для вычисления суммы
|
x |
k |
|
x |
2 |
|
x |
3 |
|
x |
k |
|
S |
|
1 x |
|
|
|
... |
|
... |
||||
|
|
|
|
|
|
|
|
|||||
k 0 |
k! |
2 |
6 |
|
k! |
|
где k! = 1·2·3·...·(k 1)·k. Напомним, что данная сумма равна ex.
Сумма содержит бесконечное число слагаемых. Но каждое следую-
щее меньше предшествующего, стремится к нулю и всё меньший |
||||||||||||||||||||
|
|
|
начало |
вклад вносит в сумму. Поэтому, начиная с некото- |
||||||||||||||||
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
рого слагаемого, отбросим остальные. Будем по- |
||||||||||||||||
|
|
|
ввод x и |
лагать, что точность вычисления суммы достаточ- |
||||||||||||||||
|
|
|
точн. |
|||||||||||||||||
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
на, если отношение очередного слагаемого к сум- |
||||||||||||||||
|
|
|
a = 1; k = 0; |
ме всех предыдущих слагаемых по модулю мень- |
||||||||||||||||
|
|
|
S = 0 |
ше числа 0, остальные слагаемые можно не учи- |
||||||||||||||||
|
|
|
|
|||||||||||||||||
|
|
|
|
|||||||||||||||||
|
|
|
|
тывать. Однако заранее нельзя определить сколь- |
||||||||||||||||
|
|
|
S = S + a |
|||||||||||||||||
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
ко слагаемых войдёт в сумму, сформулировано |
||||||||||||||||
|
|
|
|
только условие завершения циклического процес- |
||||||||||||||||
|
|
|
k = k + 1 |
|||||||||||||||||
|
|
|
са. Поэтому следует использовать оператор цикла |
|||||||||||||||||
|
|
|
|
|||||||||||||||||
|
|
|
|
с постусловием для реализации алгоритма. Выве- |
||||||||||||||||
|
|
|
|
|||||||||||||||||
|
|
|
a = ax/k |
|||||||||||||||||
|
|
|
дем рекуррентное соотношение |
|
|
|
|
|||||||||||||
|
|
|
|
|
|
|
|
|||||||||||||
|
|
|
|
|
a |
k |
|
xk |
: |
xk 1 |
|
|
|
xk (k 1)! |
|
x |
ak ak 1 |
x |
. |
|
|
|
|
|
|
|
|||||||||||||||
|
нет |
|
|
|
|
|
(k 1)! |
|
k 1 |
(k 1)! k |
|
|
||||||||
|
|
|
|a/S| |
|
ak 1 |
k! |
|
|
x |
|
|
k |
|
k |
|
|||||
|
|
|
|
|
|
|
|
|
|
|||||||||||
|
|
|
да |
В цикле (рис.7. 8) определяется значение текущего |
||||||||||||||||
|
|
|
вывод S |
слагаемого по рекуррентной формуле, если оно не |
||||||||||||||||
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
удовлетворяет условию точности, то осуществля- |
||||||||||||||||
|
|
|
конец |
ется переход к новой итерации, где в её начале это |
||||||||||||||||
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
Рис. 7.8 |
слагаемое добавляется к сумме. В противном слу- |
||||||||||||||||
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
87
чае происходит выход из цикла и вывод накопленной суммы без сла-
гаемого, вычисленного на последней итерации, т.к. оно уже удовле-
творило условию |ak/Sk-1| . До входа в цикл следует задать началь-
ные значения a = 1 (значение первого слагаемого), k = 0 (номер перво-
го слагаемого), S = 0 (чтобы получить S = a =1 на первой итерации). procedure TForm1.Button1Click(Sender: TObject);
var x, e, a, S:real; k:byte;
begin
x:=StrToFloat(Edit1.Text);
e:=StrToFloat(Edit2.Text); //точность должна быть положительной a:=1; k:=0; S:=0; //присвоение начальных значений до тела цикла repeat //начало тела цикла
S:=S+a; //добавление слагаемого к накапливаемой сумме k:=k+1; //переход к следующему номеру слагаемого
a:=a*x/k; //вычисление текущего слагаемого по рекуррентной формуле until abs(a/S)<=e; //проверка условия выхода из тела цикла
Label3.Caption:='S='+FloatTostrF(S,ffFixed,10,5); //вывод суммы
Label4.Caption:='слагаемых в сумме '+IntToStr(k); //вывод числа слаг.
Label5.Caption:='альтерн. знач. '+FloatToStr(exp(x)); //необязательно
end;
На рис. 7.9 представлены примеры работы приложения с расчё-
том суммы при трёх значениях точности и контрольным значением.
Рис. 7.9
88
Задание
I. Разработать алгоритм вычисления значений x и y параметри-
ческой функции для значений параметра t от a до b с шагом h и реа-
лизовать его в проекте
|
m |
|
|
mt |
|
|
|
|
|
|
|
|
|
|
|||||
x |
|
|
|
x |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
2 |
|
|
|
3 |
|
|
|
|
2 |
|
|
|
3 |
|
|
|
|||
|
t 1 |
|
t |
|
1 |
|
|
2t |
|
x 2cos t |
|
x cos(t 2) |
|||||||
|
|
x t |
|
|
|
||||||||||||||
1. |
|
m |
2. |
mt |
2 |
|
3. |
|
|
|
4. |
|
y 2sin t |
5. |
|
y cos(t 1) |
|||
y |
|
y |
|
|
|
|
|
2t |
|
|
|
|
|||||||
|
2 |
|
|
|
|
|
|
|
y t |
2 |
|
|
|
|
|||||
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
t(t 1) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
||
t |
3 |
1 |
|
|
|
|
|
|
|
|
|
|
|||||||
|
|
|
|
|
|
|
|
|
|
|
|
|
x m(t sin t) 6. y m(1 cos t)
|
|
e |
t |
e |
t |
|
|
|
|
|
|
|
|
|
|
|
|
||||
|
x |
|
|
|
t |
|
|
|
||
|
|
|
|
|
x t sin t cos t |
|
x m cos t |
|||
|
|
|
|
2 |
|
|
|
|
||
7. |
|
e |
t |
e |
t |
8. |
|
9. |
|
|
|
|
|
|
|
|
y sin t t cos t |
|
y msin t |
||
|
y |
|
|
|
|
|
1 |
|
|
|
|
|
|
2 |
|
|
|
|
|
||
|
|
|
|
|
|
|
|
|
|
II. Разработать алгоритм вычисления конечной суммы или произведе-
ния и реализовать его в проекте
10 |
|
sin(kx) |
|||
1. |
|||||
|
|
||||
k 1 |
|
|
k |
||
10 |
|
e |
xi |
||
6. |
|
|
|
||
(i 2)! |
|||||
i 1 |
10 |
(sin x)k |
5 |
|
xk 5 |
|
|
|
10 |
xk |
|
10 |
|
cos(kx) |
|||||||
2. |
|
|
|
3. |
|
|
|
|
|
4. |
|
|
|
5. |
|
|
|
|
|
|
k! |
|
|
|
|
|
|
|
k! |
|
k |
2 |
|||||||||
k 1 |
|
|
k 5 (k 7)! |
|
k 1 |
|
k 3 |
|
|
|||||||||||
10 |
(x 1) |
i 1 |
30 |
e |
x / k |
e |
x / k |
|
12 |
|
|
x |
2 |
|
||||||
7. |
|
|
8. |
|
|
|
|
|
1 |
|
|
|||||||||
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|||||
(i 2)! |
|
(k 2)4 |
|
|
|
|
|
|
||||||||||||
|
9. |
i |
|
|
||||||||||||||||
i 1 |
|
|
|
k 1 |
|
|
|
|
|
|
i 2 |
|
|
|
|
|
|
|
III. Разработать алгоритм вычисления бесконечной суммы с точно-
стью 0 и реализовать его в проекте. Проанализировать значение суммы и числа слагаемых в зависимости от значения точности
|
x |
2i 1 |
|
| cos(ix) | |
||
1. |
|
|
2. |
|||
(2i 1)! |
i 1 |
|||||
i 0 |
i 2 |
sin 2 (ix) 3. i3 1
i 1
|
| x |
| |
|
( 1) |
i |
x |
2i |
4. |
5. |
|
|
||||
2 |
|
(2i)! |
|
||||
i 1 |
i |
|
i 0 |
|
|
sin((2k 1)x) |
|
k |
cos((2k 1)x) |
|
|
i |
|
|
2k 1 |
|||||
6. |
7. |
( 1) |
|
8. |
x |
|
|
9. |
x |
|
|||||
2k 1 |
|
|
2k 1 |
i i! |
2k 1 |
||||||||||
k 0 |
k 0 |
|
i 1 |
k 0 |
|||||||||||
|
0 x |
|
/ 4 x |
|
|
|
|
|
x |
|
1 |
||||
|
|
|
|
|
|
|
|
||||||||
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
Предусмотреть в проектах конструкции контроля вводимых ис-
ходных данных на корректность, в т.ч. возможность «зацикливания».
89
Содержание отчёта
цель работы и задание;
для каждого из трёх заданий:
блок-схема алгоритма решения;
текст модуля проекта;
пример работы приложения с указанием компонентов;
тестирование приложения альтернативным расчётом;
выводы по работе.
Контрольные вопросы
1.Что такое повторяющийся алгоритм?
2.Каков синтаксис операторов цикла, какие конструкции реализует каждый из них и в каких ситуациях обычно используется?
3.Можно ли использовать логическую константу в условии входа или выхода из цикла, почему?
4.Опишите способы вычисления конечных и бесконечных сумм.
5.Почему в теле счётного оператора цикла не пишут оператор увели-
чения (или уменьшения) счётчика на единицу?
6.Что такое «зацикливание»?
7.Какие значения получат переменные x и y?
S:=0; n:=1; |
S:=0; n:=1; |
S:=0; n:=1; |
S:=0; n:=1; |
while n 3 do |
while n=3 do |
repeat |
repeat |
begin |
begin |
S:=S+n; |
S:=S+n; |
S:=S+n; |
S:=S+n; |
n:=n+1; |
n:=n+1; |
n:=n+1; |
n:=n+1; |
until n 3; |
until n 3; |
end; |
end; |
x:=S; y:=n; |
x:=S; y:=n; |
x:=S; y:=n; |
x:=S; y:=n; |
|
|
|
|
|
|
90