Компания ALT Linux
Опубликован: 10.04.2015 | Доступ: свободный | Студентов: 763 / 0 | Длительность: 14:03:00
Специальности: Программист, Преподаватель
Лекция 3:

Операторы управления

Рассмотрим использование оператора if на примерах3В задачах этой главы мы не будем уделять много внимания интерфейсу создаваемых программ, чтобы у читателя была возможность разобраться в алгоритмах и способах их записи на языке Free Pascal..

ЗАДАЧА 3.1. Дано вещественное число x. Для функции, график которой приведён на рис. 3.10, вычислить y = f (x).

Аналитически функцию, представленную на рис. 3.10, можно записать так:

y(x) = \begin{cases}
4,   & x \le -2, \\
x^2, & -2 < x < 1, \\
1,   & x \ge 1.
\end{cases}

Составим словесный алгоритм решения этой задачи:

  1. Начало алгоритма.
  2. Ввод числа x (аргумент функции).
  3. Если значение x меньше либо равно -2, то переход к п. 4, иначе переход к п. 5.
  4. Вычисление значения функции: y = 4, переход к п. 8.
  5. Если значение x больше либо равно 1, то переход к п. 6, иначе переход к п. 7.
  6. Вычисление значения функции: y = 1, переход к п. 8.
  7. Вычисление значения функции: y = x^2.
  8. Вывод значений аргумента x и функции y.
  9. Конец алгоритма.

Блок-схема, соответствующая описанному алгоритму, представлена на рисунке 3.11. Как видно, блок-схема нагляднее и проще для восприятия, чем словесное описание алгоритма. В дальнейшем для описания алгоритма мы часто будем использовать именно блок-схемы.

Блок-схема алгоритма решения задачи 3.1

увеличить изображение
Рис. 3.11. Блок-схема алгоритма решения задачи 3.1

Текст программы на языке Free Pascal будет иметь вид:

var
	x, y : real;
begin
	write ( ’ x= ’ );
	readln ( x );
	if x<= -2 then y:=4
	else if x>=1 then y:=1
	else y:= sqr ( x );
	writeln ( ’ x= ’, x : 5 : 2, ’    y= ’, y : 5 : 2 );
end.

Эту программу можно ввести в текстовом редакторе Geany (или в текстовом редакторе Free Pascal) и запустить на выполнение.

ЗАДАЧА 3.2. Даны вещественные числа x и y. Определить, принадлежит ли точка с координатами (x; y) заштрихованной части плоскости (рис. 3.12).

Как показано на рис. 3.12, область ограничена линиями x = -1, x = 3, y = -2 и y = 4. Значит, точка с координатами (x; y) будет принадлежать этой области, если будут выполняться следующие условия: x \ge -1, x \le 3, y \ge -2 и y \le 4. Иначе точка лежит за пределами области.

Блок-схема, описывающая алгоритм решения данной задачи, представлена на рис. 3.13.

Графическое представление задачи 3.2

увеличить изображение
Рис. 3.12. Графическое представление задачи 3.2
Алгоритм решения задачи 3.2

увеличить изображение
Рис. 3.13. Алгоритм решения задачи 3.2

Текст программы к задаче 3.2:

var x, y : real;
begin
	write ( ’ x= ’ ); readln ( x );
	write ( ’ y= ’ ); readln ( y );
	if ( x>= -1) and ( x<=3) and ( y>= -2) and ( y<=4) then
		writeln ( ’Точка принадлежит области ’ )
	else
		writeln ( ’Точка не принадлежит области ’ );
end.
ЗАДАЧА 3.3. Написать программу решения квадратного уравнения ax^2+ bx + c = 0.

Исходные данные: вещественные числа a, b и c — коэффициенты квадратного уравнения.

Алгоритм решения квадратного уравнения

увеличить изображение
Рис. 3.14. Алгоритм решения квадратного уравнения

Результаты работы программы: вещественные числа x_1 и x_2 — корни квадратного уравнения — либо сообщение о том, что корней нет.

Вспомогательные переменные: вещественная переменная d, в которой будет храниться дискриминант квадратного уравнения.

Составим словесный алгоритм решения этой задачи.

  1. Начало алгоритма.
  2. Ввод числовых значений переменных a, b и c.
  3. Вычисление значения дискриминанта d по формуле d = b^2-4ac.
  4. Если d < 0, то переход к п. 5, иначе переход к п. 6.
  5. Вывод сообщения "Действительных корней нет" и переход к п. 8.
  6. Вычисление корней x_1 = \left(-b+\sqrt{d}\right)/(2a) и x_2 =\left(-b-\sqrt{d}\right)/(2a).
  7. Вывод значений x_1 и x_2 на экран.
  8. Конец алгоритма.

Блок-схема, соответствующая этому описанию, представлена на рис. 3.14.

Текст программы, которая реализует решение квадратного уравнения:

{Описание переменных.}
var a, b, c, d, x1, x2 : real;
begin
{Ввод значения коэффициентов квадратного уравнения.}
writeln ( ’Введите коэффициенты квадратного уравнения ’ );
readln ( a, b, c );
{Вычисление дискриминанта.}
d:=b * b-4*a*c;
{Если дискриминант отрицателен,}
if d<0 then
	{то вывод сообщения, что корней нет,}
	writeln ( ’Действительных корней нет ’ )
else
begin
	{иначе вычисление корней x1, x2}
	x1:=(-b+sqrt ( d ) ) / 2 / a;
	x2:=(-b_sqrt ( d ) ) / ( 2 * a );
	{и вывод их на экран.}
	writeln ( ’X1= ’, x1 : 6 : 3, ’ -X2= ’, x2 : 6 : 3 )
end
end.
ЗАДАЧА 3.4. Составить программу нахождения действительных и комплексных корней квадратного уравнения ax^2 + bx + c = 0.

Исходные данные: вещественные числа a, b и c — коэффициенты квадратного уравнения.

Результаты работы программы: вещественные числа x_1 и x_2 — действительные корни квадратного уравнения — либо x_1 и x_2 — действительная и мнимая части комплексного числа.

Вспомогательные переменные: вещественная переменная d, в которой будет храниться дискриминант квадратного уравнения.

Можно выделить следующие этапы решения задачи:

  1. Ввод коэффициентов квадратного уравнения a, b и c.
  2. Вычисление дискриминанта d по формуле d = b^2- 4ac.
  3. Проверка знака дискриминанта. Если d \ge 0, то вычисление действительных корней:
    x_1 = \frac{-b+\sqrt{d}}{2a}\text{ и }
x_2 = \frac{-b-\sqrt{d}}{2a}

и вывод их на экран. При отрицательном дискриминанте выводится сообщение о том, что действительных корней нет, и вычисляются комплексные корни4Комплексные числа записываются в виде a+bi, где a — действительная часть комплексного числа, b — мнимая часть комплексного числа, i — мнимая единица \sqrt{-1}.

Алгоритм решения задачи 3.4

увеличить изображение
Рис. 3.15. Алгоритм решения задачи 3.4
\frac{-b}{2a}+i\frac{\sqrt{|d|}}{2a},
\frac{-b}{2a}-i\frac{\sqrt{|d|}}{2a}.

У обоих комплексных корней действительные части одинаковые, а мнимые отличаются знаком. Поэтому можно в переменной x1 хранить действительную часть числа -b/(2a), в переменной x2 — модуль мнимой части \sqrt{|d|}/(2a), а в качестве корней вывести x1+ix2 и x1-ix2.

На рис. 3.15 изображена блок-схема решения задачи. Блок 1 предназначен для ввода коэффициентов квадратного уравнения. В блоке 2 осуществляется вычисление дискриминанта. Блок 3 осуществляет проверку знака дискриминанта; если дискриминант отрицателен, то корни комплексные, их расчёт происходит в блоке 4 (действительная часть корня записывается в переменную x1, модуль мнимой — в переменную x2), а вывод — в блоке 5 (первый корень x1+ix2, второй — x1-ix2). Если дискриминант положителен, то вычисляются действительные корни уравнения (блоки 6—7) и выводятся на экран (блок 8).

Текст программы, реализующей поставленную задачу:

var a, b, c, d, x1, x2 : real;
begin
	writeln ( ’Введите_коэффициенты_квадратного_уравнения ’ );
	readln ( a, b, c );
	d:=b * b-4*a*c;
	if d<0 then
	begin
	//Если дискриминант отрицателен, то вывод сообщения,
	//что действительных корней нет, и вычисление комплексных корней.
		writeln ( ’Действительных корней нет ’ );
		{Вычисление действительной части комплексных корней.}
		x1:=-b /(2 * a );
		{Вычисление модуля мнимой части комплексных корней.}
		x2:= sqrt ( abs ( d ) ) / ( 2 * a );
		writeln ( ’Комплексные корни уравнения  ’,
		a : 1 : 2, ’ x^2+ ’, b : 1 : 2, ’ x+ ’, c : 1 : 2, ’=0 ’ );
		{Вывод значений комплексных корней в виде x1\pm ix2}
		writeln ( x1 : 1 : 2, ’+i * ( ’, x2 : 1 : 2, ’ ) ’ );
		writeln ( x1 : 1 : 2, ’- i * ( ’, x2 : 1 : 2, ’ ) ’ );
	end
	else
	begin
	{иначе вычисление действительных корней x1, x2}
		x1:=(-b+sqrt ( d ) ) / 2 / a;
		x2:=(-b_sqrt ( d ) ) / ( 2 * a );
		{и вывод их на экран.}
		writeln ( ’Действительные корни уравнения  ’,
			a : 1 : 2, ’ x^2+ ’, b : 1 : 2, ’ x+ ’, c : 1 : 2, ’=0 ’ );
		writeln ( ’X1= ’, x1 : 1 : 2, ’ X2= ’, x2 : 1 : 2 )
	end
end.
ЗАДАЧА 3.5. Составить программу для решения кубического уравнения ax^3 + bx^2 + cx + d = 0.

Кубическое уравнение имеет вид

ax^3 + bx^2 + cx + d = 0 ( 3.1)

После деления на a уравнение (3.1) принимает канонический вид:

x^3 + rx^2 + sx + t = 0 ( 3.2)

где r = b/a, s = c/a, t = d/a. В уравнении (3.2) сделаем замену x = y - r/3 и получим приведённое уравнение:

y^3 + py + q = 0, ( 3.3)

где

p = \frac{3s-r^2}{3}, q = \frac{2r^{3}}{27} - \frac{rs}{3}+t.

Число действительных корней приведённого уравнения (3.3) зависит от знака дискриминанта D = (p/3)^3+ (q/2)^2 приведённого кубического уравнения (табл. 3.1).

Таблица 3.1. Количество корней кубического уравнения
Дискриминант Количество действительных корней Количество комплексных корней
D > 0 1 2
D < 0 3

Корни приведённого уравнения могут быть рассчитаны по формулам Кардано:

\begin{aligned}
y_{1} & = u+v\\
y_{2} & = \frac{-{u+v}}{2}+\frac{u-v}{2}i\sqrt{3}\\
y_{3} & = \frac{-{u+v}}{2}-\frac{u-v}{2}i\sqrt{3}
\end{aligned} ( 3.4)

где

u=\sqrt[{3}]{-q/2+\sqrt{D}},
v=\sqrt[{3}]{-q/2-\sqrt{D}}.

При отрицательном дискриминанте уравнение (3.1) имеет три действительных корня, но они будут вычисляться через вспомогательные комплексные величины. Чтобы избавиться от этого, можно воспользоваться формулами:

\begin{aligned}
y_1&=2\sqrt[3]{\rho}\cos\left(\frac{\varphi}{3}\right),\\
y_2&=2\sqrt[3]{\rho}\cos\left(\frac{\varphi}{3}+\frac{2\pi}{3}\right),\\
y_3&=2\sqrt[3]{\rho}\cos\left(\frac{\varphi}{3}+\frac{4\pi}{3}\right),
\end{aligned} ( 3.5)

где

\rho =\sqrt{\frac{-p^3}{27}}, \cos(\varphi)=\frac{-q}{2\rho}.

Таким образом, при положительном дискриминанте кубического уравнения (3.3) расчёт корней будем вести по формулам (3.4), а при отрицательном — по формулам (3.5).

После расчёта корней приведённого уравнения (3.3) по формулам (3.4) или (3.5) необходимо по формулам

x_{k}=y_{k}-\frac{r}{3}, k=1,2,3\ldots

перейти к корням заданного кубического уравнения (3.1).

Блок-схема решения кубического уравнения представлена на рис. 3.16.

Алгоритм решения кубического уравнения

увеличить изображение
Рис. 3.16. Алгоритм решения кубического уравнения

Описание блок-схемы. В блоке 1 вводятся коэффициенты кубического уравнения, в блоках 2—3 рассчитываются коэффициенты канонического и приведённого уравнений. Блок 4 предназначен для вычисления дискриминанта. В блоке 5 проверяется знак дискриминанта кубического уравнения. Если он отрицателен, то корни вычисляются по формулам (3.5) (блоки 6—7). При положительном значении дискриминанта расчёт идет по формулам (3.4) (блок 9, 10). Блоки 8 и 11 предназначены для вывода результатов на экран.

Текст программы с комментариями приведён ниже55При расчёте величин u и v в программе предусмотрена проверка значения подкоренного выражения. Если \frac{-q}{2}\pm \sqrt{D} > 0, то u=\sqrt[3]{\frac{-q}{2}+ \sqrt{D}} > 0, а v=\sqrt[3]{\frac{-q}{2}- \sqrt{D}} > 0. Если \frac{-q}{2}\pm \sqrt{D} < 0, то u=\sqrt[3]{\frac{-q}{2}+ \sqrt{D}} > 0, а v=\sqrt[3]{\frac{-q}{2}- \sqrt{D}} > 0. Соответственно, при нулевом значении подкоренного выражения u и v обращаются в ноль..

var
	a, b, c, d, r, s, t, p, q, ro, f i, x1, x2, x3, u, v, h, g : real;
begin
	//Ввод коэффициентов кубического уравнения.
	write ( ’ a= ’ ); readln ( a );
	write ( ’ b= ’ ); readln ( b );
	write ( ’ c= ’ ); readln ( c );
	write ( ’ d= ’ ); readln ( d );
	//Расчёт коэффициентов канонического уравнения по 3.2.
	r :=b/a; s := c /a; t :=d/a;
	//Вычисление коэффициентов приведённого уравнения 3.3.
	p :=(3 * s - r * r ) / 3;
	q:=2* r * r * r /27- r * s/3+ t;
	//Вычисление дискриминанта кубического уравнения.
	d :=( p /3) * sqr ( p/3)+ sqr ( q / 2 );
	//Проверка знака дискриминанта,
	//ветка then реализует формулы (3.5),
	//ветка else — формулы 3.4
	if d<0 then
	begin
		ro := sqrt (-p * p * p / 27 );
		//Следующие два оператора реализуют расчёт угла fi,
		//сначала вычисляется величина косинуса угла,
		//затем вычисляется его арккосинус через арктангенс.
		fi :=-q /(2 * ro );
		fi := pi /2-arctan ( fi / sqrt (1 - fi * fi ) );
		//Вычисление действительных корней уравнения x1, x2 и x3
		x1 :=2 * exp (1/3 * ln ( ro ) ) * cos ( fi /3) - r / 3;
		x2 :=2 * exp (1/3 * ln ( ro ) ) * cos ( fi /3+2 * pi /3) - r / 3;
		x3 :=2 * exp (1/3 * ln ( ro ) ) * cos ( fi /3+4 * pi /3) - r / 3;
		writeln ( ’ x1= ’, x1 : 1 : 3, ’ x2= ’, x2 : 1 : 3, ’ x3= ’, x3 : 1 : 3 );
end
else
begin
	//Вычисление u и v с проверкой знака
	// подкоренного выражения.
	if -q/2+ sqrt ( d)>0 then
		u:=exp (1/3 * ln (-q/2+ sqrt ( d ) ) )
	else
		if -q/2+ sqrt ( d)<0 then
			u:=-exp (1/3 * ln ( abs(-q/2+ sqrt ( d ) ) ) )
		else
			u : = 0;
	if -q/2- sqrt ( d)>0 then
		v:=exp (1/3 * ln (-q/2- sqrt ( d ) ) )
	else
		if -q/2- sqrt ( d)<0 then
			v:=-exp (1/3 * ln ( abs(-q/2- sqrt ( d ) ) ) )
		else
			v : = 0;
	//Вычисление действительного корня кубического уравнения.
	x1:=u+v-r / 3;
	//Вычисление действительной и
	// мнимой части комплексных корней.
	h:=-(u+v)/2 - r / 3;
	g :=(u - v )/2 * sqrt ( 3 );
	writeln ( ’ x1= ’, x1 : 1 : 3, ’ x2= ’, h : 1 : 3, ’+i*  ’, g : 1 : 3,
				’ x3= ’, h : 1 : 3, ’ -i*  ’, g : 1 : 3 );
	end
end.
ЗАДАЧА 3.6. Заданы коэффициенты a, b и c биквадратного уравнения ax^4 + bx^2+ c = 0. Найти все его действительные корни.

Входные данные: a, b, c. Выходные данные: x1, x2, x3, x4.

Для решения биквадратного уравнения необходимо заменой y = x^2 привести его к квадратному уравнению ay^2 + by + c = 0 и решить это уравнение.

Опишем алгоритм решения этой задачи (рис. 3.17):

  1. Ввод коэффициентов биквадратного уравнения a, b и c (блок 1).
  2. Вычисление дискриминанта уравнения d (блок 2).
  3. Если d < 0 (блок 3), вывод сообщения, что корней нет (блок 4), а иначе определяются корни соответствующего квадратного уравнения y_1 и y_2 (блок 5).
  4. Если y_1 < 0 и y_2 < 0 (блок 6), то вывод сообщения, что корней нет (блок 7).
  5. Если y_1 \ge 0 и y_2  \ge 0 (блок 8), то вычисляются четыре корня по формулам \pm \sqrt{y_1}, \pm \sqrt{y_2} (блок 9) и выводятся значения корней (блок 10).
  6. Если условия 4) и 5) не выполняются, то необходимо проверить знак y_1. Если y_1 > 0 (блок 11), то вычисляются два корня по формуле \pm \sqrt{y_1} (блок 12), иначе (если y_2 > 0) вычисляются два корня по формуле \pm \sqrt{y_2} (блок 13).
  7. Вывод вычисленных значений корней (блок 14).
Алгоритм решения биквадратного уравнения

увеличить изображение
Рис. 3.17. Алгоритм решения биквадратного уравнения

Текст программы на языке Free Pascal с комментариями:

//Описание переменных:
//a,b,c - коэффициенты биквадратного уравнения,
//d - дискриминант,
//x1,x2,x3,x4 - корни биквадратного уравнения,
//y1,y2 - корни квадратного уравнения ay^2+by+c=0.
var
	a, b, c, d, x1, x2, x3, x4, y1, y2 : real;
begin
	//Ввод коэффициентов уравнения.
	writeln ( ’Введите коэффициенты биквадратного уравнения ’ );
	readln ( a, b, c );
	//Вычисление дискриминанта.
	d:=b * b-4*a*c;
	//Если он отрицателен,
	if d<0 then
		//вывод сообщения "Корней нет"
		writeln ( ’Корней нет ’ )
	//Если дискриминант >= 0,
	else
	begin
		//вычисление корней квадратного уравнения.
		y1:=(-b+sqrt ( d ) ) / 2 / a;
		y2:=(-b-sqrt ( d ) ) / ( 2 * a );
		//Если оба корня квадратного уравнения < 0,
		if ( y1 <0) and ( y2 <0) then
			//вывод сообщения "Корней нет".
			writeln ( ’Корней нет ’ )
		//Если оба корня квадратного уравнения >= 0,
		else if ( y1>=0) and ( y2>=0) then
		begin
			//вычисление четырех корней биквадратного уравнения.
			x1:= sqrt ( y1 );
			x2:=-x1;
			x3:= sqrt ( y2 );
			x4:=-sqrt ( y2 );
			//Вывод корней биквадратного уравнения на экран.
			writeln ( ’X1= ’, x1 : 6 : 3, ’ X2= ’, x2 : 6 : 3 );
			writeln ( ’X3= ’, x3 : 6 : 3, ’ X4= ’, x4 : 6 : 3 );
		end
		//Если не выполнились оба условия
		// 1. y1<0 И y2<0
		// 2. y1>=0 И y2>=0,
		//то проверяем условие y1>=0
		else if ( y1>=0) then
		//Если оно истинно
		begin
			x1:= sqrt ( y1 );
			x2:=-x1;
			writeln ( ’X1= ’, x1 : 6 : 3, ’   X2= ’, x2 : 6 : 3 );
		end
		else
		//Если условие y1>=0 ложно, то
		begin
			x1:= sqrt ( y2 );
			x2:=-x1;
			writeln ( ’X1= ’, x1 : 6 : 3, ’    X2= ’, x2 : 6 : 3 );
		end
	end
end.
Юрий Шутиков
Юрий Шутиков

По первому тесту выполнил дважды задания. Результат получается правильный (проверял калькулятором). Пишет, что "Задание не проверено" и предлагает повторить. 
 

Евгений Силуков
Евгений Силуков

Еще в декабре выполнил тест №1, а его все так и не проверили.