- •Отображает данные, вводимые в ручную, во время обработки с устройств любого типа (клавиатура, переключатели, кнопки, световое перо, полоски со штрих кодом и т.д.).
- •Символ отображает хранимые данные в виде, пригодном для обработки. Носитель данных не определен. В схемах алгоритмов он предназначен для обозначения ввода-вывода данных в случае использования запоминающего устройства, управляемого процесса.
- •Тема 1. Основные этапы решения задач на ЭВМ
- •Постановка задачи разработки программного обеспечения
- •Анализ формальной постановки задачи
- •Выбор или разработка математической модели и метода решения
- •Разработка алгоритма
- •Базовые структуры алгоритма
- •Тема 2. Жизненный цикл программы. Критерии качества программы.
- •Техническое задание и спецификация программы
- •Разработка проекта программной системы
- •Программирование (кодирование) или программная реализация алгоритмов
- •Тестирование и отладка
- •Эксплуатация и сопровождение
- •Критерии качества программного обеспечения
- •Тема 3. Схемы алгоритмов, данных, программ
- •Символы данных
- •Символы процесса
- •Символы линий
- •Специальные символы
- •Правила применения символов в схемах
- •Правила выполнения соединений
- •Специальные условные обозначения
- •Тема 4. Язык программирования высокого уровня Си
- •Общие сведения о языке Си
- •Алфавит языка Си
- •Грамматика для описания языка, синтаксические диаграммы
- •Структура программы на языке Си
- •Имена объектов в программе
- •Выражения, операции и приоритеты
- •Тема 5. Стандартные типы данных
- •Тема 6. Составные типы данных
- •Данные регулярного типа (массивы)
- •Строки
- •Данные комбинированного типа (структуры)
- •Перечисления
- •Объединения
- •Указатели
- •Тема 7. Представление основных управляющих структур программирования
- •Оператор присваивания
- •Составной оператор
- •Оператор перехода Goto
- •Условный оператор If
- •Оператор выбора switch
- •Операторы цикла while, do – while, for
- •Операторы прерывания циклов
- •Форматированный ввод данных
- •Форматированный вывод данных
- •Преобразование типов
- •Инициализация данных
- •Тема 8. Функции
- •Определение функций в языке Си
- •Вызов функций в языке Си
- •Рекурсивные функции
- •Тема 9. Файлы
- •Тема 10. Приемы программирования. Примеры алгоритмов
- •Алгоритмы сортировки
- •Алгоритмы поиска
- •Динамические структуры данных
- •Линейные списки
- •Стек, очередь, дек
- •Деревья
- •Приложение 1. Стандартные библиотеки языка Си
- •Приложение 2. Примеры реализации алгоритмов
- •Не рекурсивный алгоритм решения задачи Ханойская башня.
- •Рекурсивный алгоритм решения задачи Ханойская башня.
- •Приложение 3. Лабораторные работы
- •Лабораторная работа №1
- •Лабораторная работа №2
- •Лабораторная работа №3
- •Лабораторная работа №4
- •Лабораторная работа №5
- •Лабораторная работа №6
- •Лабораторная работа №7
- •Лабораторная работа №8
- •Лабораторная работа №9
- •Лабораторная работа №10
- •Лабораторная работа №11
- •Лабораторная работа №12
- •Список литературы
printf("\n ");
puts ("Читаем из файла");
while ((fnumber = fgetc(file))!= EOF) // Пока не конец файла читаем число //из файла
{ printf ("%x\t",fnumber); // Выводим его на экран
} fsum = fsum + fnumber; // Считаем сумму чисел fclose (file); // Закрыли файл
file = fopen( file_name, "a" ); // Открываем файл для дополнения fputs("Сумма значений равна \n", file); // Выводим в конец файла fprintf(file, "%s\n", &fsum);
printf("\n ");
fclose (file); // Закрыли файл puts("Готово"); system("pause");
}
На экране будет отображен следующий диалог:
Сколько чисел будем вводить : 5 Введите число 1 : 5 Введите число 2 : 4 Введите число 3 : 3 Введите число 4 : 2 Введите число 5 : 1
Читаем из файла 5 4 3 2 1
Готово!
При этом файл a.txt будет сожержать следующие строки:
5
4
3
2
1 Сумма значений равна
15
В зависимости от компилятора символы, записанные в файл могут не отображаться в привычной числовой форме.
Тема 10. Приемы программирования. Примеры алгоритмов
Алгоритмы сортировки
Задача сортировки ставится следующим способом. Пусть имеется массив целых или вещественных чисел a1,...,an. Требуется переставить элементы этого массива так, чтобы после перестановки они были упорядочены по неубыванию: а1 ≤ a2 ≤ ... ≤an или невозрастанию: а1 ≥ a2 ≥ ... ≥an. Если числа попарно различны, то говорят об упорядочении по возрастанию или убыванию. В дальнейшем
137
будем рассматривать задачу упорядочения по неубыванию, т.к. остальные задачи решаются аналогично. Существует множество алгоритмов сортировки, каждый из которых имеет свои характеристики по скорости. Рассмотрим самые простые алгоритмы, в порядке увеличения скорости их работы.
Сортировка обменами (пузырьком)
Этот алгоритм считается самым простым и самым медленным. Шаг сортировки состоит в проходе снизу вверх по массиву. При этом просматриваются пары соседних элементов. Если элементы некоторой пары находятся в неправильном порядке, то они меняются местами.
После первого прохода по массиву "вверху" (в начале массива) оказывается самый "легкий" (минимальный) элемент – отсюда аналогия с пузырьком, который всплывает (рис.37). Следующий проход делается до второго сверху элемента, таким образом, второй по величине элемент поднимается на правильную позицию и так далее.
|
|
0 |
15 |
8 |
Исходный массив |
6 |
16 |
5 |
19 |
||
|
|
10 |
19 |
20 |
|||||||
№ шага |
1: |
0 |
15 |
8 |
10 |
19 |
20 |
6 |
5 |
16 |
19 |
|
1: |
0 |
15 |
8 |
10 |
19 |
20 |
5 |
6 |
16 |
19 |
|
1: |
0 |
15 |
8 |
10 |
19 |
5 |
20 |
6 |
16 |
19 |
|
1: |
0 |
15 |
8 |
10 |
5 |
19 |
20 |
6 |
16 |
19 |
|
1: |
0 |
15 |
8 |
5 |
10 |
19 |
20 |
6 |
16 |
19 |
|
1: |
0 |
15 |
5 |
8 |
10 |
19 |
20 |
6 |
16 |
19 |
|
1: |
0 |
5 |
15 |
8 |
10 |
19 |
20 |
6 |
16 |
19 |
|
2: |
0 |
5 |
15 |
8 |
10 |
19 |
6 |
20 |
16 |
19 |
|
2: |
0 |
5 |
15 |
8 |
10 |
6 |
19 |
20 |
16 |
19 |
|
2: |
0 |
5 |
15 |
8 |
6 |
10 |
19 |
20 |
16 |
19 |
|
2: |
0 |
5 |
15 |
6 |
8 |
10 |
19 |
20 |
16 |
19 |
|
2: |
0 |
5 |
6 |
15 |
8 |
10 |
19 |
20 |
16 |
19 |
|
3: |
0 |
5 |
6 |
15 |
8 |
10 |
19 |
16 |
20 |
19 |
|
3: |
0 |
5 |
6 |
15 |
8 |
10 |
16 |
19 |
20 |
19 |
|
3: |
0 |
5 |
6 |
8 |
15 |
10 |
16 |
19 |
20 |
19 |
|
4: |
0 |
5 |
6 |
8 |
15 |
10 |
16 |
19 |
19 |
20 |
|
4: |
0 |
5 |
6 |
8 |
10 |
15 |
16 |
19 |
19 |
20 |
|
|
0 |
5 |
Результат |
10 |
15 |
16 |
19 |
19 |
20 |
|
|
|
6 |
8 |
||||||||
Рис. 37. Сортировка массива методом «пузырька»
138
Проходы делаются по все уменьшающейся нижней части массива до тех пор, пока в ней не останется только один элемент. На этом сортировка заканчивается, так как последовательность упорядочена по возрастанию.
//процедура сортировки обменами (пузырьком) void SortBubble (int count, int* pArr)
{
int trash = 0;
for (int i = 0; i < count; i++) // i - номер прохода
{ for (int j=0; j < count-i-1; j++) // внутренний цикл прохода { if (pArr[j] > pArr[j+1]) //если "левый" больше "правого"
{ trash = pArr[j]; //меняем местами элементы pArr[j] = pArr[j+1];
} } }
}
pArr[j+1] = trash;
Сортировка выбором
Сортировка выбором выполняется несколько быстрее, чем сортировка методом пузырька. Алгоритм заключается в следующем: нужно найти элемент массива, имеющий наименьшее значение, переставить его с первым элементом, затем проделать тоже самое, начав со второго элемента и т.д. Таким образом, создается отсортированная последовательность путем присоединения к ней одного элемента за другим в правильном порядке. На i-м шаге выбирается наименьший из элементов a[i] ... a[n] и меняем его местами с a[i]. Последовательность шагов изображена на рис.38.
|
|
16 |
6 |
6 |
Исходный массив |
6 |
3 |
3 |
|||
|
|
20 |
2 |
19 |
13 |
||||||
№ шага |
1: |
2 |
6 |
6 |
20 |
16 |
19 |
13 |
6 |
3 |
3 |
|
|||||||||||
|
2: |
2 |
3 |
6 |
20 |
16 |
19 |
13 |
6 |
6 |
3 |
|
3: |
2 |
3 |
3 |
20 |
16 |
19 |
13 |
6 |
6 |
6 |
|
4: |
2 |
3 |
3 |
6 |
16 |
19 |
13 |
20 |
6 |
6 |
|
5: |
2 |
3 |
3 |
6 |
6 |
19 |
13 |
20 |
16 |
6 |
|
6: |
2 |
3 |
3 |
6 |
6 |
6 |
13 |
20 |
16 |
19 |
|
7: |
2 |
3 |
3 |
6 |
6 |
6 |
13 |
20 |
16 |
19 |
|
8: |
2 |
3 |
3 |
6 |
6 |
6 |
13 |
16 |
20 |
19 |
139
9: |
2 |
3 |
3 |
6 |
6 |
6 |
13 |
16 |
19 |
20 |
10: |
2 |
3 |
3 |
6 |
6 |
6 |
13 |
16 |
19 |
20 |
|
2 |
3 |
3 |
Результат |
6 |
13 |
16 |
19 |
20 |
|
|
6 |
6 |
||||||||
Рис. 38. Результат сортировки выбором
Вне зависимости от номера текущего шага i, последовательность a[0]...a[i] является упорядоченной. Таким образом, на (n-1)-м шаге вся последовательность, кроме a[n] оказывается отсортированной, а a[n] стоит на последнем месте по праву: все меньшие элементы уже ушли влево.
//процедура сортировки выбором
void SortSelect(int count, int* pArr)
{
int i1,temp; int jmax;
for (int i = count - 1; i > 0; i--) // i - номер текущего шага
{ jmax = 0;
for (int j = 0; j <= i; j++)
{
} if (pArr [jmax] < pArr [j]) i1 = j;
temp = pArr [i1]; pArr [i1] = pArr [i];
}} pArr [i] = temp;
Сортировка простыми вставками
Просматривается массив и каждый новый элемент a[i] вставляется на подходящее место в уже упорядоченную совокупность a[1],...,a[i-1]. Это место определяется последовательным сравнением a[i] с упорядоченными элементами a[1],...,a[i-1]. Таким образом в начале массива "вырастает" отсортированная последовательность.
Однако в сортировке пузырьком или выбором можно было четко заявить, что на i-м шаге элементы a[1]...a[i-1]стоят на правильных местах и никуда более не переместятся. Здесь же подобное утверждение будет более слабым: последовательность a[1]...a[i-1] упорядочена. При этом по ходу алгоритма в нее будут вставляться (см. название метода) все новые элементы.
Рассмотрим действия алгоритма на i-м шаге. Как говорилось выше, последовательность к этому моменту разделена на две части: готовую a[1]...a[i-1] и неупорядоченную a[i]...a[n].
140
На следующем, i-м каждом шаге алгоритма берем a[i] и вставляем на нужное место в готовую часть массива. Поиск подходящего места для очередного элемента входной последовательности осуществляется путем последовательных сравнений с элементом, стоящим перед ним. В зависимости от результата сравнения элемент либо остается на текущем месте (вставка завершена), либо они меняются местами и процесс повторяется (рис.39).
Таким образом, в процессе вставки мы "просеиваем" элемент X к началу массива, останавливаясь в случае, когда
1.Hайден элемент, меньший X.
2.Достигнуто начало последовательности.
|
12 |
16 |
10 |
Исходный массив |
9 |
11 |
10 |
11 |
|||
№ шага |
9 |
10 |
9 |
||||||||
12 |
16 |
10 |
9 |
10 |
9 |
9 |
11 |
10 |
11 |
||
2: |
|||||||||||
3: |
10 |
12 |
16 |
9 |
10 |
9 |
9 |
11 |
10 |
11 |
|
4: |
9 |
10 |
|
|
10 |
9 |
9 |
11 |
10 |
11 |
|
5: |
9 |
|
|
16 |
9 |
9 |
11 |
10 |
11 |
||
6: |
9 |
9 |
9 |
10 |
10 |
16 |
9 |
11 |
10 |
11 |
|
7: |
9 |
12 |
16 |
11 |
10 |
11 |
|||||
8: |
9 |
9 |
9 |
10 |
10 |
11 |
|
16 |
10 |
11 |
|
9: |
9 |
9 |
9 |
10 |
10 |
10 |
11 |
|
16 |
11 |
|
10: |
9 |
9 |
9 |
10 |
|
|
16 |
||||
|
9 |
9 |
9 |
10 |
Результат |
11 |
11 |
12 |
16 |
||
|
10 |
10 |
|||||||||
|
|
|
|
Рис. 39. Сортировка массива простыми вставками |
|||||||
//процедура сортировки простыми вставками void SortInsert (int count, int* pArr)
{
int temp, j;
for (int i = 1; i < n; i++) // цикл проходов, i - номер прохода
{ temp = pArr[i];
j = i-1; // поиск места элемента в готовой последовательности while (j >= 0 && pArr[j] > temp)
{ pArr[j+1] = pArr[j]; // сдвигаем элемент направо, пока не дошли } --j;
// место найдено, вставить элемент } pArr[j+1] = temp;
}
141
