Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
ПРограмирование 1 блок.docx
Скачиваний:
6
Добавлен:
31.07.2019
Размер:
194.07 Кб
Скачать

1.Структура программы на языке С++.

#include <имя библиотеки 1>

#include <имя библиотеки 2>

...

#include "имя подключаемого файла 1"

#include "имя подключаемого файла 2"

...

// прототипы функций (заголовки)

// глобальные идентификаторы (типы, переменные и т.д.)

void main()

{

// описание переменных

// раздел операторов

}

// реализация функций

Программа на языке Си это текстовый файл с расширением. c

Текст программы имеет определенную структуру:

1. заголовок

2. включение необходимых внешних файлов

3. ваши определения для удобства работы

4. объявление глобальных переменных

Перед использованием переменной в Си её необходимо объявить! Т.е. указать компилятору какой тип данных она может хранить и как она называется.

Глобальные переменные объявляются, вне какой либо функции. Т.е. не после фигурной скобки {. Они доступны в любом месте программы, значит можно читать их значения и присваивать им значения там, где требуется.

5. описание функций - обработчиков прерываний

6. описание других функций используемых в программе

7. функция main - это единственный обязательный пункт !

Это не жесткий порядок, а ориентировочный!

Иногда п. 6 - это прототипы функций, а сами функции описываются полностью после п. 7.

Прототип функции - показывает образец того, как применять функцию в программе, какие значения в нее передаются и, если она возвращает какое-то значение, то прототип указывает тип возвращаемых данных. Прототип не имеет скобок { }, а после скобок ( ) ставится знак ;.

Функция - имеет { "тело" } в фигурных скобках. Тело - это код на Си определяющий то, что делает функция. Знак «;» после функции не ставится.

Программа на Си начинает работу с функции main(), по необходимости из main() вызываются другие функции программы, по завершении работы функции программа возвращается в main(), в то место, откуда функция была вызвана.

main(){

... какой то код программы ...

вызов функции_1; /* программа перейдет в функцию_1 строка программы */

// будет выполнятся после

// возврата из функции_1

... какой то код программы ...

}

Функции могут вызываться не только из main(), но и из других функций.

Программа на C++ обычно состоит из большого числа исходных файлов, каждый из которых содержит описания типов, функций, переменных и констант. Чтобы имя можно было использовать в разных исходных файлах для ссылки на один и тот же объект, оно должно быть описано как внешнее. Например:

extern double sqrt(double);

extern instream cin;

Самый обычный способ обеспечить согласованность исходных файлов - это поместить такие описания в отдельные файлы, называемые заголовочными (или хэдер) файлами, а затем включить, то есть скопировать, эти заголовочные файлы во все файлы, где нужны эти описания. Например, если описание sqrt хранится в заголовочном файле для стандартных математических функций math.h, и вы хотите извлечь квадратный корень из 4, можно написать:

#include

//...

x = sqrt(4);

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

В команде включения include имя файла, заключенное в угловые скобки, например , относится к файлу с этим именем в стандартном каталоге (часто это /usr/include/CC); на файлы, находящиеся в каких-либо других местах ссылаются с помощью имен, заключенных в двойные кавычки. Например:

#include "math1.h"

#include "/usr/bs/math2.h"

включит math1.h из текущего пользовательского каталога, а math2.h из каталога /usr/bs.

Здесь приводится очень маленький законченный пример программы, в котором строка определяется в одном файле, а ее печать производится в другом. Файл header.h определяет необходимые типы:

// header.h

extern char* prog_name;

extern void f();

В файле main.c находится главная программа:

// main.c

#include "header.h"

char* prog_name = "дурацкий, но полный";

main()

{

f();

}

а файл f.c печатает строку:

// f.c

#include

#include "header.h"

void f()

{

cout << prog_name << "\n";

}

Скомпилировать и запустить программу вы можете например так:

$ CC main.c f.c -o silly

$ silly

дурацкий, но полный

$

2. Основные и дополнительные операции в языке С++.

Наряду с общепринятыми арифметическими и логическими операциями, в языке Си++ имеется набор операций для работы с битами – поразрядные И, ИЛИ, ИСКЛЮЧАЮЩЕЕ ИЛИ и НЕ, а также сдвиги.

Особняком стоит операция sizeof. Эта операция позволяет определить, сколько памяти занимает то или иное значение. Например:

sizeof(long);

// сколько байтов занимает тип long

sizeof (b);

// сколько байтов занимает переменная b

Операция sizeof в качестве аргумента берет имя типа или выражение. Аргумент заключается в скобки (если аргумент – выражение, скобки не обязательны). Результат операции – целое число, равное количеству байтов, которое необходимо для хранения в памяти заданной величины.

Ниже приводятся все операции языка Си++.

Арифметические операции

+ сложение

- вычитание

* умножение

/ деление

Операции сложения, вычитания, умножения и деления целых и вещественных чисел. Результат операции – число, по типу соответствующее большему по разрядности операнду. Например, сложение чисел типа short и long в результате дает число типа long.

% остаток

Операция нахождения остатка от деления одного целого числа на другое. Тип результата – целое число.

- минус

+ плюс

Операция "минус" – это унарная операция, при которой знак числа изменяется на противоположный. Она применима к любым числам со знаком. Операция "плюс" существует для симметрии. Она ничего не делает, т.е. примененная к целому числу, его же и выдает.

++ увеличить на единицу, префиксная и

постфиксная формы

-- уменьшить на единицу, префиксная и

постфиксная формы

Эти операции иногда называют "автоувеличением" (инкремент) и "автоуменьшением" (декремент). Они увеличивают (или, соответственно, уменьшают) операнд на единицу. Разница между постфиксной (знак операции записывается после операнда, например x++ ) и префиксной (знак операции записывается перед операндом, например --y ) операциями заключается в том, что в первом случае результатом является значение операнда до изменения на единицу, а во втором случае – после изменения на единицу.

Операции сравнения

== равно

!= не равно

< меньше

> больше

<= меньше или равно

>= больше или равно

Операции сравнения. Сравнивать можно операнды любого типа, но либо они должны быть оба одного и того же встроенного типа ( сравнение на равенство и неравенство работает для двух величин любого типа), либо между ними должна быть определена соответствующая операция сравнения. Результат – логическое значение true или false.

Логические операции

&& логическое И

|| логическое ИЛИ

! логическое НЕ

Логические операции конъюнкции, дизъюнкции и отрицания. В качестве операндов выступают логические значения, результат – тоже логическое значение true или false .

Битовые операции

& битовое И

| битовое ИЛИ

^ битовое ИСКЛЮЧАЮЩЕЕ ИЛИ

~ битовое НЕ

Побитовые операции над целыми числами. Соответствующая операция выполняется над каждым битом операндов. Результатом является целое число.

<< сдвиг влево

>> сдвиг вправо

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

Условная операция

операнд1?операнд2:операнд3

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

Последовательность

, последовательность

Выполнить выражение до запятой, затем выражение после запятой. Два произвольных выражения можно поставить рядом, разделив их запятой. Они будут выполняться последовательно, и результатом всего выражения будет результат последнего выражения.

Операции присваивания

= присваивание

Присвоить значение правого операнда левому. Результат операции присваивания – это значение правого операнда.

+=, -=, *=, /=, %=, |=, &=, ^=, <<=, >>=

выполнить операцию и присвоить

Выполнить соответствующую операцию с левым операндом и правым операндом и присвоить результат левому операнду. Типы операндов должны быть такими, что, во-первых, для них должна быть определена соответствующая арифметическая операция, а во-вторых, результат может быть присвоен левому операнду.

3. Стандартные математические функции в языке С++.

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

{loadposition adsense2}

Abc (x) – модуль,

ceil (x) – округление к ближайшему целому не меньше х,

сos (x) - извлечение косинуса числа х,

exp (x) - експанента числа х,

Fabs (x) – модуль для дробного х,

floor (x) – наибольшее целое не превышающее х,

fmod (x,y) – остаток от деления х на у,

log (x) – (обозначение в математике - ln (x)) - извлечение натурального логарифма из числа х,

Log 10 (x) – (обозначение в математике - lg (x)) - извлечение десятичного логарифма из числа х,

pow (x,y) – возведение х в степень у,

sin (x) - получение синуса числа х,

sqrt (x) - извлечение корня квадратного из числа х,

tan (x) – (обозначение в математике - tg(x)) - получение тангенса числа х.

4. Функции ввода-вывода в языке С++.

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

За организацию ввода информации отвечает класс istream (input stream, входной поток), за организацию вывода – ostream (output stream, выходной поток). Эти и некоторые другие классы для организации ввода-вывода описаны в заголовочном файле iostream.h. В частности, используемый для ввода с клавиатуры объект cin является экземпляром класса istream, а используемый для вывода на экран объект cout – экземпляр класса ostream.

В заголовочном файле fstream.h описаны классы ifstream и ofstream, которые могут использоваться для организации файлового ввода-вывода.

Общая схема организации ввода-вывода такова:

1. Создать объект для организации ввода-вывода.

2. Убедиться в том, что объект создан успешно (с помощью метода is_open()).

3. Выполнить необходимые операции по вводу данных (с помощью оператора >>) или по выводу данных (с помощью оператора <<).

4. Закончить работу с объектом (с помощью метода close()).

Пример 1. Ввод данных о студенте из файла.

// 1. Создать объект для ввода данных из файла

ifstream in("student.txt");

// 2. Убедиться, что объект создан успешно

if (in.is_open())

{

STUDENT student;

// 3. Выполнить операции по вводу данных

in >> student.LastName

in >> student.FirstName;

in >> student.MiddleName;

in >> student.Number;

// 4. Закончить работу с объектом

in.close();

}

else

{

cerr << "Ошибка ввода из файла";

}

Пример 2. Вывод данных о студенте в файл.

// 1. Создать объект для вывода данных в файл

ofstream out("student2.txt");

// 2. Убедиться, что объект создан успешно

if (out.is_open())

{

// 3. Выполнить операции по выводу данных

out << student.LastName << endl;

out << student.FirstName << endl;

out << student.MiddleName << endl;

out << student.Number << endl;

// 4. Закончить работу с объектом

out.close();

}

else

{

cerr << "Ошибка вывода в файл";

}

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

Пример 3. Функция для ввода данных о студенте из потока

STUDENT ReadStudent(istream &in)

{

STUDENT student;

in >> student.LastName;

in >> student.FirstName;

in >> student.MiddleName;

in >> student.Number;

return student;

}

Пример 4. Ввод данных о студенте с клавиатуры

Student stud;

cout << "Введите данные о студенте\n";

stud = ReadStudent(cout);

Пример 5. Ввод данных о студенте из файла

Student student;

ifstream in("student.txt");

stud = ReadStudent(in);

in.close();

Аналогично можно реализовать и использовать функции для вывода данных.

В языке программирования C++ имеется возможность ещё больше упростить вызов функций для организации ввода-вывода. Для этого используется механизм перегрузки операторов. Благодаря этому программист имеет возможность заменить вызовы функций, осуществляющих ввод-вывод структурных типов данных, на привычные операторы << и >>.

Для перегрузки операторов << и >> нужно оформить функции для ввода-вывода по следующему образцу:

// функция-оператор для ввода данных из потока

istream& operator >> (istream & out, тип & имя)

{

out >> ...

return out;

}

// функция-оператор для вывода данных в поток

ostream& operator << (ostream & out, тип имя)

{

out << ...

return out;

}

Пример 6. Функция-оператор для ввода данных о студенте из потока

istream& operator >> (istream &in, STUDENT & Stud)

{ in >> Stud.LastName;

in >> Stud.FirstName;

in >> Stud.MiddleName;

in >> Stud.Number;

return in;

}

Пример 7. Ввод данных о студенте с клавиатуры

Student student;

cout << "Введите данные о студенте\n";

cin >> student;

Пример 8. Ввод данных о студенте из файла

Student student;

ifstream in("student.txt");

in >> student;

in.close();

Аналогично можно реализовать и использовать функции-операторы для вывода данных.

5. Логические операции и операции отношения.

Язык С имеет ровно три логические операции: это

&& или (AND);

|| или (OR);

! или (NOT).

Как принято еще называть логические операции?

Операция "&&" или операция "AND" называется еще операцией "и" или логическим умножением.

Операция "||" или операция "OR" называется еще операцией "или" или логическим сложением.

Операция "!quot; или операция "NOT" называется еще операцией "не" или логическим отрицанием.

Таблицы истинности логических операций в языке С.

Разберемся, почему они так называются? Будем считать, что истина это "1", а ложь это "0".

Операция "&&" называется логическим умножением потому, что выполняется таблица истинности этой операции, очень напоминающая таблицу обыкновенного умножения из арифметики.

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

1 && 1 = 1

0 && 1 = 0

1 && 0 = 0

0 && 0 = 0

Операция "||" называется логическим сложением потому, что выполняется таблица истинности этой операции, очень напоминающая таблицу обыкновенного сложения из арифметики.

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

1 || 1 = 1

0 || 1 = 1

1 || 0 = 1

0 || 0 = 0

Операция "!" называется логическим отрицанием потому, что выполняется следующая таблица истинности.

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

!1 = 0

!0 = 1

Логическая операция "исключающее или" в языке С.

Кроме трех расмотренных выше классических логических операций в языке С используется еще четвертая логическая операция: "исключающее или".

Если обычно принято

операцию логическое умножение обозначать как "X AND Y",

операцию логическое сложение как "X OR Y",

а логическое отрицание как "NOT X",

то операцию "исключающее или" обозначают как "X XOR Y".

Сделаем одно очень выжное замечание. Оно касается логической операции XOR. В языке С нет знака логической операции XOR. Однако, она может быть реализована с помощью операций AND, OR и NOT. Покажем теперь таблицу истинности этой новой логической операции в языке С.

1 XOR 1 = 0

0 XOR 1 = 1

1 XOR 0 = 1

0 XOR 0 = 0

Отсюда видно, что, если оба входящих в выражение высказывания истинны или оба ложны, то есть однакового значения истинности, то результат будет в этом случае ложным. То есть как бы отрицается утверждение: оба высказывания имеют одинаковый смысл истинности.

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

Логические операции и операции отношения имеют более низкий приоритет, чем арифметические операции. Это значит, что выражение 200>120+50 равносильно выражению 200>(120+50).

Принято следующее старшинство операций отношения и логических операций:

! - самая старшая из логических операций

Далее старшинство операций распределяется так:

>

<

>=

<=

. Затем уже идут операции:

==

!=

и самая младшая операция - это ||.

В логических выражениях можно использовать скобки, которые имеют наивысший приоритет. Это положение известно еще из арифметики. Оно сохраняется и здесь. Использование скобок делает выражение более понятным и удобным для чтения. Поэтому рекомекндуется использовать скобки. Условные и логические выражения часто используются в операторе условного перехода if и в других операторах.

Отметим еще одну очень важную особенность операторов && и ||. Если при вычислении операции X && Y первое выражение X окажется нулевым (то есть ложным), то значение второго выражения Y никак не повлияет на результат. Это следует из таблицы истинности операции логическое умножение. Смотрите таблицу истинности этой операции. Поэтому действительно можно игнорировать второе выражение. Аналогично обстоит дело и с оператором ||. Так, если значение первого операнда ненулевое, то значение второго операнда так же не влияет на результат. Потому он так же не вычисляется и игнорируется. Это также следует из таблицы истинности операции логическое сложение. Поэтому нужно учитывать этот факт и не изменять во втором операторе какую-либо переменную, пользуясь операцией ++.

6. Преобразование типов в языке С++.

При выполнении операций происходят неявные преобразования типов в следующих случаях:

- при выполнении операций осуществляются обычные арифметические преобразования (которые были рассмотрены выше);

- при выполнении операций присваивания, если значение одного типа присваивается переменной другого типа;

- при передаче аргументов функции.

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

В операциях присваивания тип значения, которое присваивается, преобразуется к типу переменной, получающей это значение. Допускается преобразования целых и плавающих типов, даже если такое преобразование ведет к потере информации.

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

Преобразование целого со знаком к плавающему типу происходит без потери] информации, за исключением случая преобразования значения типа long int или unsigned long int к типу float, когда точность часто может быть потеряна.

Преобразование целых типов без знака. Целое без знака преобразуется к более короткому целому без знака или со знаком путем усечения старших битов. Целое без знака преобразуется к более длинному целому без знака или со знаком путем дополнения нулей слева.

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

Целые значения без знака преобразуются к плавающему типу, путем преобразования целого без знака к значению типа signed long, а затем значение signed long преобразуется в плавающий тип. Преобразования из unsigned long к типу float, double или long double производятся с потерей информации, если преобразуемое значение больше, чем максимальное положительное значение, которое может быть представлено для типа long.

Преобразования плавающих типов. Величины типа float преобразуются к типу double без изменения значения. Величины double и long double преобразуются к float c некоторой потерей точности. Если значение слишком велико для float, то происходит потеря значимости, о чем сообщается во время выполнения.

При преобразовании величины с плавающей точкой к целым типам она сначала преобразуется к типу long (дробная часть плавающей величины при этом отбрасывается), а затем величина типа long преобразуется к требуемому целому типу. Если значение слишком велико для long, то результат преобразования не определен.

Преобразования из float, double или long double к типу unsigned long производится с потерей точности, если преобразуемое значение больше, чем максимально возможное положительное значение, представленное типом long.

Преобразование типов указателя. Указатель на величину одного типа может быть преобразован к указателю на величину другого типа. Однако результат может быть не определен из-за отличий в требованиях к выравниванию и размерах для различных типов.

Указатель на тип void может быть преобразован к указателю на любой тип, и указатель на любой тип может быть преобразован к указателю на тип void без ограничений. Значение указателя может быть преобразовано к целой величине. Метод преобразования зависит от размера указателя и размера целого типа следующим образом:

- если размер указателя меньше размера целого типа или равен ему, то указатель преобразуется точно так же, как целое без знака;

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

Целый тип может быть преобразован к адресному типу по следующим правилам:

- если целый тип того же размера, что и указатель, то целая величина просто рассматривается как указатель (целое без знака);

- если размер целого типа отличен от размера указателя, то целый тип сначала преобразуется к размеру указателя (используются способы преобразования, описанные выше), а затем полученное значение трактуется как указатель.

Преобразования при вызове функции. Преобразования, выполняемые над аргументами при вызове функции, зависят от того, был ли задан прототип функции (объявление "вперед") со списком объявлений типов аргументов.

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

Эти преобразования выполняются независимо для каждого аргумента. Величины типа float преобразуются к double, величины типа char и short преобразуются к int, величины типов unsigned char и unsigned short преобразуются к unsigned int. Могут быть также выполнены неявные преобразования переменных типа указатель. Задавая прототипы функций, можно переопределить эти неявные преобразования и позволить компилятору выполнить контроль типов.

Преобразования при приведении типов. Явное преобразование типов может быть осуществлено посредством операции приведения типов, которая имеет формат:

( имя-типа ) операнд .

В приведенной записи имя-типа задает тип, к которому должен быть преобразован операнд.

Пример:

int i=2; long l=2; double d; float f; d=(double)i * (double)l; f=(float)d;

В данном примере величины i,l,d будут явно преобразовываться к указанным в круглых скобках типам.

7. Разновидности условного оператора if. Привести примеры.

Формат оператора:

if (выражение) оператор-1; [else оператор-2;]

Выполнение оператора if начинается с вычисления выражения.

Далее выполнение осуществляется по следующей схеме:

- если выражение истинно (т.е. отлично от 0), то выполняется оператор-1.

- если выражение ложно (т.е. равно 0),то выполняется оператор-2.

- если выражение ложно и отсутствует оператор-2 (в квадратные скобки заключена необязательная конструкция), то выполняется следующий за if оператор.

После выполнения оператора if значение передается на следующий оператор программы, если последовательность выполнения операторов программы не будет принудительно нарушена использованием операторов перехода.

Пример:

if (i < j) i++: else { j = i-3; i++; }

Этот пример иллюстрирует также и тот факт, что на месте оператор-1, так же как и на месте оператор-2 могут находиться сложные конструкции.

Допускается использование вложенных операторов if. Оператор if может быть включен в конструкцию if или в конструкцию else другого оператора if. Чтобы сделать программу более читабельной, рекомендуется группировать операторы и конструкции во вложенных операторах if, используя фигурные скобки. Если же фигурные скобки опущены, то компилятор связывает каждое ключевое слово else с наиболее близким if, для которого нет else.

Примеры:

int main ( ) { int t=2, b=7, r=3; if (t>b) { if (b < r) r=b; } else r=t; return (0); }

В результате выполнения этой программы r станет равным 2.

Если же в программе опустить фигурные скобки, стоящие после оператора if, то программа будет иметь следующий вид:

int main ( ) { int t=2,b=7,r=3; if ( a>b ) if ( b < c ) t=b; else r=t; return (0); }

В этом случае r получит значение равное 3, так как ключевое слово else относится ко второму оператору if, который не выполняется, поскольку не выполняется условие, проверяемое в первом операторе if.

Следующий фрагмент иллюстрирует вложенные операторы if:

char ZNAC; int x,y,z; : if (ZNAC == '-') x = y - z; else if (ZNAC == '+') x = y + z; else if (ZNAC == '*') x = y * z; else if (ZNAC == '/') x = y / z; else ...

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

8.

Оператор цикла while или цикл while - цикл, повторяющий одно и то же действие, пока условие продолжения цикла while остаётся истинным.

// форма записи цикла while

while (/*условие продолжения цикла while*/)

{

/*блок операторов*/;

/*управление условием*/;

}

Условие продолжения цикла должно быть истинно "true", как только условие стало ложным, выполняется выход из цикла. Также как и в условных операторах выбора, фигурные скобочки могут опускаться в том случае, если тело цикла - это один оператор. Но как правило в цикле выполняется несколько операторов, так как кроме выполнения полезного действия необходимо делать условие цикла while ложным, иначе цикл будет бесконечным, а это, в свою очередь, приведет к зависанию программы.

Рассмотрим применение цикла while на примере движения автомобиля. На псевдокоде, то это будет так:

// Пока скорость движения автомобиля меньше 60 км/ч, продолжать наращивать скорость.

Истинным условием цикла, в данном случае, является скорость автомобиля меньше 60 км/ч, а ложным - скорость автомобиля больше или равно 60 км/ч. Повторение цикла будет продолжаться до тех пор пока скорость автомобиля не станет больше или равно 60 км/ч, после наступления этого момента условие цикла станет ложным, и программа выйдет из цикла. Рассмотрим фрагмент кода на C++ с циклом while решающим поставленную задачу.

Для начала в строке 1 была объявлена и инициализирована переменная speed. В строке 2 программа проверяет условие цикла while, 5 < 60 = true. Программа входит в цикл и выполняет оператор в строке 3. Теперь уже speed = 15. Опять выполняется проверка 15 < 60 = true. Условие истинно, значение в переменной изменяется, speed = 25. Таким образом, выполняются последовательные повторения цикла, переменная speed ещё принимает такие значения: 35, 45, 55, 65. Последнее изменение переменной speed приводит к тому, что условие в цикле while становится ложным 65 < 60 = false, и производится выход из цикла while. Таким образом, выполнилось 6 повторений, при этом speed = 65; - с таким значением переменной закончилась работа цикла while. Давайте запрограммируем эту задачу, и убедимся в достоверности всего выше сказанного

// while.cpp: определяет точку входа для консольного приложения.

#include "stdafx.h"

#include <iostream>

using namespace std;

int main(int argc, char* argv[])

{

int speed = 5, count = 1;

while ( speed < 60 )

{

speed += 10; // приращение скорости

cout << count <<"-speed = " << speed << endl;

count++; // подсчёт повторений цикла

}

system("pause");

return 0;

}

в строке 14 добавил переменную-счётчик, для подсчёта прохождений цикла. Тело цикла увеличилось, поэтому пришлось поставить фигурные скобочки.

9. Выражения. Привести примеры выражений.

Выражения

Программа оперирует с данными. Числа можно складывать, вычитать, умножать, делить. Из разных величин можно составлять выражения, результат вычисления которых – новая величина. Приведем примеры выражений:

X * 12 + Y // значение X умножить на 12 и к результату прибавить значение Y

val < 3 // сравнить значение val с 3

-9 // константное выражение -9

Выражение, после которого стоит точка с запятой – это оператор-выражение. Его смысл состоит в том, что компьютер должен выполнить все действия, записанные в данном выражении, иначе говоря, вычислить выражение.

x + y – 12; // сложить значения x и y и затем вычесть 12

a = b + 1; // прибавить единицу к значению b и запомнить результат в переменной a

Выражения – это переменные, функции и константы, называемые операндами, объединенные знаками операций. Операции могут быть унарными – с одним операндом, например, минус; могут быть бинарные – с двумя операндами, например сложение или деление. В Си++ есть даже одна операция с тремя операндами – условное выражение. Чуть позже мы приведем список всех операций языка Си++ для встроенных типов данных. Подробно каждая операция будет разбираться при описании соответствующего типа данных. Кроме того, ряд операций будет рассмотрен в разделе, посвященном определению операторов для классов. Пока что мы ограничимся лишь общим описанием способов записи выражений.

В типизированном языке, которым является Си++, у переменных и констант есть определенный тип. Есть он и у результата выражения. Например, операции сложения ( + ), умножения ( * ), вычитания ( - ) и деления ( / ), примененные к целым числам, выполняются по общепринятым математическим правилам и дают в результате целое значение. Те же операции можно применить к вещественным числам и получить вещественное значение.

Операции сравнения: больше ( > ), меньше ( < ), равно ( == ), не равно ( != ) сравнивают значения чисел и выдают логическое значение: истина ( true ) или ложь ( false ).

10. Разновидности операторов цикла.

1)Разновидности циклов в Visual Basic

Кроме структур принятия решений, существуют еще одна разновидность управляющих конструкций, называемая циклом.

Цикл - это алгоритмическая структура, при помощи которой реализуется многократное повторение блоков операторов.

В языке Visual Basic существует три основных вида циклов, которые реализуется при помощи конструкций For:Next, Do:Loop и While:Wend.

Цикл For:Next. Используется в том случае, когда количество повторов заданного блока операторов известно заранее. Данная конструкция выглядит следующим образом:

For счетчик = начальное значение To конечное значение [Step шаг]

Операторы1

[Exit For]

Операторы2

Next [счетчик]

Когда приведенные операторы выполняются первый раз, то переменной счетчику присваивается начальное значение, после чего возможны два варианта действий. Если в результате проверки условия счетчик > конечное значение было получено значение True, то происходит завершение цикла, при этом блоки операторы1 и операторы2 ни разу не выполняются. С другой стороны, если результатом проверки условия является False, то в этом случае блоки операторов выполняются первый раз, после чего происходит переход на начало цикла. Далее значение переменной-счетчика увеличивается на шаг, расположенный после ключевого слова Step (в случае его отсутствия устанавливается шаг = 1). После этого снова проверяется истинность условия счетчик > конечное значение и т.д., окончание цикла происходит в тот момент, когда результатом данной проверки станет значение True.

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

If условие Then Exit For

Если результатом проверки условия будет значение True, то выполнение цикла будет прекращено, причем блок операторы1 будет выполнен очередной раз, а блок операоры2 - нет.

Цикл Do:Loop. Применяется в том случае, когда число повторений операторов тела цикла заранее неизвестно. Существуют четыре разновидности данной конструкции. При использовании первых двух цикл либо выполнится много раз, либо не выполнится вообще.

Do Until условие

Операторы

Loop

Если результатом проверки условия является значение False, то блок операторы выполняется, иначе осуществляется переход на оператор, расположенный после служебного слова Loop. С другой стороны, если первая проверка условия даст результат True, то цикл не выполнится ни разу.

Do While условие

Операторы

Loop

Если условие истинно, то происходит выполнение блока операторы, если же ложно, то есть результатом проверки является False, то цикл не выполниться ни разу.

В случае использования последних двух конструкций цикл будет выполнен хотя бы один раз.

Do

Операторы

Loop Until условие

Блок операторы выполняется до тех пор, пока результатом проверки условия является значение False, иначе выполнение цикла заканчивается.

Do

Операторы

Loop While условие

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

Цикл While:Wend. Также используется в том случае, когда число повторений операторов тела цикла заранее неизвестно, и имеет следующий синтаксис:

While условие

Операторы

Wend

Если результатом проверки условия является значение True, то блок операторы выполняется, иначе осуществляется переход на оператор, расположенный после служебного слова Wend. С другой стороны, если первая проверка условия даст результат False, то цикл не выполнится ни разу.

2) Цикл- многократное прохождение по одному и тому же коду программы. Циклы необходимы программисту для многократного выполнения одного и того же кода, пока истинно какое-то условие. Если условие всегда истинно, то такой цикл называется бесконечным, у такого цикла нет точки выхода.

В языке программирования С++ существуют такие циклы:

цикл for

цикл while

цикл do .. while

Тело цикла будет выполняться до тех пор, пока условие будет истинно(т. е. true).

// форма записи оператора цикла for:

for (/*выражение1*/; /*выражение2*/; /*выражение3*/ )

{

/*один оператор или блок операторов*/;

}

Если в теле цикла for должен выполнится один оператор, тогда фигурные скобки можно опустить:

for (/*выражение1*/; /*выражение2*/; /*выражение3*/)

/*один оператор*/;

Рассмотрим подробно три выражения записанные в круглых скобках цикла for! Выражение1 - объявление (и) или инициализация, ранее объявленной, переменной-счетчика, которая будет отвечать за истинность условия в цикле for. Пример:

int counter = 0; // отсюда видно, что была объявлена переменная counter типа int и инициализирована значением 0

еременная-счетчик всегда должна иметь целочисленный тип данных. Если переменная была объявлена в цикле (все равно в каком), по завершении цикла эта переменная будет уничтожена.

Разница между объявлением и инициализацией переменной:

counter; // объявление переменой count

counter = 9; // инициализация целочисленной переменой count значением 9.

Выражение2 - это условие продолжения цикла for, оно проверяется на истинность.

counter < 10; // условие истинно пока count строго меньше десяти!

Выражение3 изменяет значение переменной-счетчика. Без выражения3 цикл считается бесконечным, так как изменение содержимого переменной count выполняться не будет, и если изначально условие было истинным, то цикл будет бесконечным, иначе программа даже не войдет в цикл. Выражения 1, 2, 3 отделяются друг от друга обязательными разделителями, точкой с запятой. Тело цикла обрамляется фигурными скобочками, если тело цикла состоит из одного оператора ,то фигурные скобочки не нужны. Под изменением значения переменной подразумевается уменьшение или приращение значения , например:

for ( int counter = 0; counter < 15; counter++) // выполняется приращение переменной counter с шагом 1 от 0 до 15

"++" это операция инкремента, увеличение значения переменной на единицу

"--" это операция декремента, уменьшение значения переменной на единицу

Очень часто неправильно интерпретируется запись пределов в цикле for, в нашем случае приращение переменной counter выполняется с шагом 1 от 0 до 15. Обратите внимание на конечный предел. В условии продолжения цикла стоит знак отношения строго меньше, а значит, когда значение в переменной counter будет равно 14, выполнится выход из цикла.

// for.cpp: определяет точку входа для консольного приложения.

#include "stdafx.h"

#include <iostream>

using namespace std;

int main(int argc, char* argv[])

{

for (int counter = 0; counter < 15; counter ++ ) // начало цикла

cout << " " << counter; // тело цикла

cout << endl;

system("pause");

return 0;

}

В строках 9, 10 записан цикл for, причём без фигурных скобочек. А раз отсутствуют фигурные скобочки, значит, телом цикла является следующий оператор, после заголовка цикла, в нашем случае - это оператор вывода:

cout << " " << counter; // тело цикла

Заголовком цикла for является строка 9:

for (int counter = 0; counter < 15; counter ++ ) // заголовок цикла

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

Оператор цикла while или цикл while - цикл, повторяющий одно и то же действие, пока условие продолжения цикла while остаётся истинным.

// форма записи цикла while

while (/*условие продолжения цикла while*/)

{

/*блок операторов*/;

/*управление условием*/;

}

Условие продолжения цикла должно быть истинно "true", как только условие стало ложным, выполняется выход из цикла. Также как и в условных операторах выбора, фигурные скобочки могут опускаться в том случае, если тело цикла - это один оператор. Но как правило в цикле выполняется несколько операторов, так как кроме выполнения полезного действия необходимо делать условие цикла while ложным, иначе цикл будет бесконечным, а это, в свою очередь, приведет к зависанию программы.

Рассмотрим применение цикла while на примере движения автомобиля. На псевдокоде, то это будет так:

// Пока скорость движения автомобиля меньше 60 км/ч, продолжать наращивать скорость.

Истинным условием цикла, в данном случае, является скорость автомобиля меньше 60 км/ч, а ложным - скорость автомобиля больше или равно 60 км/ч. Повторение цикла будет продолжаться до тех пор пока скорость автомобиля не станет больше или равно 60 км/ч, после наступления этого момента условие цикла станет ложным, и программа выйдет из цикла. Рассмотрим фрагмент кода на C++ с циклом while решающим поставленную задачу.

Для начала в строке 1 была объявлена и инициализирована переменная speed. В строке 2 программа проверяет условие цикла while, 5 < 60 = true. Программа входит в цикл и выполняет оператор в строке 3. Теперь уже speed = 15. Опять выполняется проверка 15 < 60 = true. Условие истинно, значение в переменной изменяется, speed = 25. Таким образом, выполняются последовательные повторения цикла, переменная speed ещё принимает такие значения: 35, 45, 55, 65. Последнее изменение переменной speed приводит к тому, что условие в цикле while становится ложным 65 < 60 = false, и производится выход из цикла while. Таким образом, выполнилось 6 повторений, при этом speed = 65; - с таким значением переменной закончилась работа цикла while. Давайте запрограммируем эту задачу, и убедимся в достоверности всего выше сказанного

// while.cpp: определяет точку входа для консольного приложения.

#include "stdafx.h"

#include <iostream>

using namespace std;

int main(int argc, char* argv[])

{

int speed = 5, count = 1;

while ( speed < 60 )

{

speed += 10; // приращение скорости

cout << count <<"-speed = " << speed << endl;

count++; // подсчёт повторений цикла

}

system("pause");

return 0;

}

в строке 14 добавил переменную-счётчик, для подсчёта прохождений цикла. Тело цикла увеличилось, поэтому пришлось поставить фигурные скобочки.

Цикл do while отличается от цикла while тем, что в цикле do while сначала выполняется тело цикла, а затем проверяется условие продолжения цикла. Из-за такой особенности цикл do while называют циклом с постусловием. Таким образом, если условие цикла do while заведомо ложное, то хотя бы один раз блок операторов в теле цикла do while выполнится. В итоге цикл do while отличается от цикла while структурой. Если в цикле while сначала выполняется проверка условия продолжения цикла, и если условие истинно, то только тогда выполняется тело цикла. Цикл do while работает с точностью да наоборот, сначала выполняется тело цикла, а потом проверяется условие, вот почему тело цикла do while, хотя бы раз, выполнится.

?1

2

3

4

5

6 // форма записи оператора цикла do while:

do // начало цикла do while

{

/*блок операторов*/;

}

while (/*условие выполнения цикла*/); // конец цикла do while

В начале цикла do while пишется зарезервированное слово do, после идут фигурные скобочки, которые можно опускать, в случае использования одного оператора в теле цикла do while. После закрывающей фигурной скобочки, обозначающей конец тела цикла do while, стоит условие цикла do while, после которого обязательно нужно ставить точку с запятой. Рассмотрим программу на С++ с циклом do while, которая выполняет некоторые транзакции с денежным счётом в банке.

// do_while.cpp: определяет точку входа для консольного приложения.

#include "stdafx.h"

#include <iostream>

#include <ctime>

using namespace std;

int main(int argc, char* argv[])

{

srand(time(0));

int balance = 8; // баланс

do // начало цикла do while

{

cout << "balance = " << balance << endl; // показать баланс

int removal = rand() % 3; // переменная, для хранения вычитаемого значения

cout << "removal = " << removal << endl; // показать вычитаемое значение

balance -= removal; // управление условием

}

while ( balance > 0 ); // конец цикла do while

system("pause");

return 0;

}

В строке 11 объявлена переменная balance, она отвечает за остаток денежных средств на счету. С 12-й по 19-ю строки записан цикл do while. В цикле do while выполняются все транзакции со счётом balance, а именно - перевод денежных средств на какой-то другой счёт, строка 17. Строка 14 показывает остаток денежных средств на счету balance. В строке 15 объявлена переменная, в которой хранится вычитаемое значение, причём это значение генерируется случайно в интервале [0;2]. Переменная removal один раз объявляется в теле цикла do while, и каждый раз при повторении цикла эта переменная не переобъявляется. А вот её значение меняется, в зависимости от того, какое число сгенерировалось. В строке 19 записано условие цикла do while, как только условие станет ложным, программа передаст управление следующему оператору, после цикла do while, строка 20.

11. Получение случайного числа. Привести пример.

Для того, чтобы получить случайное число можно, конечно, написать и свою функцию, а можно использовать и стандартные библиотечные. Мы же с вами не будем "изобретать велосипед", и поэтому будем пользоваться только стандартными библиотечными функциями. Итак, для генерации случайных чисел в С++ используют функцию rand(), описанную в библиотеке stdlib.h. Как она работает, рассмотрим на простейшем примере

#include <iostream>

#include <stdlib.h>

using namespace std;

int main()

{

int m;

m = rand();

cout << m << endl;

return 0;

}

Как видите, тут все просто: подключаем необходимую библиотеку, через директиву препроцессора #include и используем функцию rand() в программе. Попробуйте запустить программу и посмотреть выработанное ею число. А потом попробуйте запустить программу еще несколько раз. Наверное, вы заметили, что при каждом новом запуске функция rand() генерирует одно и то же число. Да, это действительно так! Но почему? Давайте разбираться вместе.

Технический момент. Т.к. rand() - это функция, то у нее есть свой прототип (описание), в котором указывается, что она может получать в качестве аргумента (аргументов) и что возвращает. Вот ее прототип (его можно найти и самостоятельно в файле stdlib.h, который обычно находится в папке include вашей среды программирования):

int rand(void);

Как видите, функция возвращает целые числа (от 0 до 32767), в качестве аргументов она не может ничего принимать, т.е. внутри скобок будет всегда пусто.

Продолжаем разбираться. Дабы понять, почему функция rand() всегда нам возвращает одно и то же число, заглянем внутрь ее. Вот, что мы там увидим

#define RAND_MAX 32767

unsigned long next = 1;

int rand(void)

{

next = next * 1103515245m;

return((unsigned int)(next / 65536)2768);

}

Не будем вдаваться в подробности кода. Скажу лишь то, что полученное случайное число с помощью этой функции, зависит от стартового числа next, которое, как вы видите, установлено в единицу. Отсюда и следует, что числа всегда получаются одинаковыми. Для того, чтобы избежать этой проблемы, в паре с rand() нужно использовать функцию srand(). Вот ее прототип

void srand(unsigned int);

А вот и ее внутренность

void srand(unsigned int seed)

{

next = seed;

}

Как видите, эта функция изменяет стартовое число next, присваивая ему другую величину, получаемую функцией в качестве аргумента. В принципе, это число можно вводить каждый раз вручную, например, так

#include <iostream>

#include <stdlib.h>

using namespace std;

int main()

{

int m, seed;

cout << "Enter seed: ";

cin >> seed;

srand(seed);

m = rand();

cout << m << endl;

return 0;

}

В этом случае, вводя разные значения переменной seed, мы будем получать различные случайные величины на выходе. Как вы понимаете, это не очень удобно. Чаще всего в качестве передаваемой величины в функцию srand() используют системное время в секундах. Согласитесь, что это наилучший способ, т.к. это число будет всегда разным, а соответственно, мы будем получать на выходе из rand() случайные числа.

Теперь рассмотрим вот такой вопрос. Допустим, что нам нужно генерировать число не на всем допустимом интервале, а только в каком-то определенном, к примеру, от 0 до 9 включительно. Как мы поступим в данном случае? У функции rand() есть свой синтаксис

m = a + rand() % b;

где a - это начальная точка, с которой начинается генерация,

b - это величина сдвига, определяющая интервал, на котором будет производиться генерация.

В нашем случае a = 0 (это число идет включительно), b = 10 (а это будет не включительно, т.к. это не конечная точка, а величина сдвига. Если от 0 отложить 10 чисел, то последним будет 9 включительно). Если бы нужно было генерировать числа в интервале, к примеру, от 30 до 50 включительно, то было бы так

m = 30 + rand() % 21;

#include <iostream>

#include <stdlib.h>

#include <time.h>

using namespace std;

int main()

{

int m;

srand(time(NULL));

for(int i = 0; i < 10; i++)

{

m = 30 + rand() % 21;

cout << m << endl;

}

return 0;

}

12. Одномерные массивы. Объявление массивов. Инициализация.

Массив – это совокупность данных, которая обладает следующими свойствами:

все элементы массива имеют один и тот же тип;

массив имеет одно имя для всех элементов;

доступ к конкретному элементу массива осуществляется по индексу (индексам).

1. Объявление массива

Объявление массива имеет следующий синтаксис:

<спецификация типа> <имя> [<константное выражение>];

<спецификация типа> <имя> [ ];

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

Объявление массива может иметь одну из двух синтаксических форм, указанных выше. Квадратные скобки, следующие за <именем>, – признак того, что переменная является массивом. <Константное выражение>, заключенное в квадратные скобки определяет число элементов в массиве. Индексация элементов массива в языке C++ начинается с нуля. Таким образом, последний элемент массива имеет индекс на единицу меньше, чем число элементов массива.

Во второй синтаксической форме константное выражение в квадратных скобках опущено. Эта форма может быть использована, если в объявлении массива присутствует инициализатор, либо массив объявляется как формальный параметр функции, либо данное объявление является ссылкой на объявление массива где-то в другом месте программы. Однако для многомерного массива может быть опущена только первая размерность.

Многомерный массив, или массив массивов, объявляется путем задания последовательности константных выражений в квадратных скобках, следующей за <именем>:

<спецификация типа> <имя> [<константное выражение>][<константное выражение>] ... ;

Каждое <константное выражение> определяет количество элементов в данном измерении массива, поэтому объявление двумерного массива содержит два константных выражение, трехмерного – три и т.д.

Массив может состоять из элементов любого типа, кроме типа void и функций, т.е. элементы массива могут иметь базовый, перечислимый, структурный тип, быть объединением, указателем или массивом.

Примеры объявлений массивов int x[10]; // Одномерный массив из 10 целых чисел. Индексы меняются от 0 до 9.

double y[2][10]; // Двумерный массив вещественных чисел из 2 строк и 10 столбцов.