- •Дискретная математика
- •6.050102 “Компьютерная инженерия” содержание
- •1 Теория множеств 7
- •2 Математическая логика 15
- •3 Формальные теории 35
- •4 Теория графов 47
- •5 Элементы теории чисел 80
- •6 Теория алгоритмов 121
- •Введение
- •1 Теория множеств
- •1.1 Множества и подмножества
- •1.1.1 Элементы множества
- •1.2 Аксиомы теории множеств
- •1.3 Способы задания множеств
- •1.4 Операции над множествами
- •1.5 Элементы алгебры множеств
- •1.5.1 Определение алгебры множеств
- •1.5.2 Основные законы алгебры множеств
- •1.5.3 Принцип двойственности
- •2 Математическая логика
- •2.1 Функции алгебры логики (булевые функции)
- •2.1.1 Способы задания булевых функций
- •2.1.2 Логические функции одной переменной
- •2.1.3 Логические функции двух переменных
- •2.2.6 Функционально полные системы булевых функций
- •2.3 Алгебра буля
- •2.3.1 Определение алгебры. Теорема Стоуна
- •2.3.2 Законы алгебры логики
- •2.3.3 Разложения функций по переменным
- •2.3.4 Приведение логических функций
- •2.3.5 Импликанты и имплициенты булевых функций
- •2.3.6 Методы минимизации логических функций
- •2.4 Алгебра жегалкина
- •2.4.1 Преобразование функций в алгебре Жегалкина
- •2.4.2 Переход от булевой алгебры к алгебре Жегалкина
- •3 Формальные теории
- •3.1 Основные принципы построения формальных теорий исчисления
- •3.2 Определение исчисления высказываний
- •3.2.1 Метатеоремы исчисления высказываний
- •3.2.2 Схемы исчисления высказываний
- •3.3 Исчисление предикатов
- •3.3.1 Определение формальной теории pl
- •3.3.2 Принцип резолюции в исчислении предикатов
- •3.3.3 Схемы доказательств в исчислении предикатов
- •4 Теория графов
- •4.1 История теории графов
- •4.2 Основные определения
- •4.3 Способы представления графов
- •4.3.1 Матрицей смежности
- •4.3.2 Матрицей инцидентности
- •4.4 Пути в графах
- •4.4.1 Задача о кратчайшем пути
- •4.4.2 Алгоритм Дейкстры нахождения кратчайшего пути в графе
- •4.5 Транспортные сети
- •4.5.1 Потоки в транспортных сетях
- •4.5.2 Задача нахождения наибольшего потока в транспортной сети
- •4.5.3 Алгоритм Форда и Фалкерсона нахождения максимального потока транспортной сети
- •4.5.4 Транспортная задача
- •4.6 Обходы в графах
- •4.6.1 Эйлеровы графы
- •4.6.2 Алгоритм Флёри нахождения эйлерова цикла
- •4. Если получился цикл, но не ейлеров, то отбрасываем данную последнюю вершину и повторяем пункт 2.
- •4.6.3 Гамильтоновы циклы
- •4.6.4 Метод ветвей и границ.
- •4.6.5 Метод ветвей и границ в задаче о коммивояжёре
- •4.7 Деревья
- •4.7.1 Построение экономического дерева
- •4.7.2 Алгоритм Краскала
- •5 Элементы теории чисел
- •5.1 Модулярная арифметика
- •5.1.1 Алгоритм Евклида для нахождения наибольшего общего делителя
- •5.1.2 Вычисление обратных величин
- •5.1.3 Основные способы нахождения обратных величин
- •5.1.4 Китайская теорема об остатках
- •5.2 Кодирование
- •5.2.1 Оптимальное кодирование
- •5.3 Обнаружение и исправление ошибок
- •5.3.1 Общие понятия
- •5.3.2 Линейные групповые коды
- •5.3.2 Код Хэмминга
- •5.3.3 Циклические коды
- •5.3.4 Построение и декодирование конкретных циклических кодов
- •5.4 Сжатие информации
- •5.4.1 Исключение повторения строк в последующих строках
- •5.4.2 Алгоритм lzw
- •6 Теория алгоритмов
- •6.1. Основные понятия
- •6.1.1 Основные требования к алгоритмам
- •6.1.2 Блок–схемы алгоритмов
- •6.1.3 Представление данных
- •6.1.4 Виды алгоритмов
- •6.1.5 Правильность программ
- •6.1.6 Эффективность алгоритмов
- •6.1.7 Сходимость, сложность, надежность
- •6.2 Универсальные алгоритмы
- •6.2.1 Основные понятия
- •6.2.2 Машины Тьюринга
- •6.2.3 Рекурсивные функции
- •6.2.5 Тезис Черча-Тьюринга
- •6.2.6 Проблема самоприменимости
- •6.3 Языки и грамматики
- •6.3.1 Общие понятия
- •6.3.2 Формальные грамматики
- •6.3.3 Иерархия языков
- •6.4 Параллельные вычисления
- •Рекомендованная литература
5.1.4 Китайская теорема об остатках
Любое неотрицательное целое число, не превосходящее произведения модулей, можно однозначно восстановить, если известны его вычеты по этим модулям. Этот результат был известен еще в древнем Китае и носит название китайской теоремы об остатках. Теорема была предложена китайским математиком первого века Сун Це. Китайская теорема об остатках является мощным криптографическим инструментом.
Она формулируется следующим образом.
Пусть m1, m2, … , m t – модули (целые числа, большие 1), которые являются попарно взаимно простыми, т.е. НОД (mi, mj,) = 1 при i j.
Пусть а1, а2, … , а t – тоже целые числа, такие, что 0 ≤ а i ≤ m i.
Пусть М = m1 • m2 • … • m t – произведение всех m i . Обозначим М i = M / m i.
И пусть N i будет обратным к М i (mod m i), i = 1, 2, … , t, т.е.
М i • N i 1 (mod m i).
Так как НОД (М i , m i) = 1, то обратный элемент N i существует и легко находится по алгоритму Евклида из соотношения
М i • N i + m i • n i = 1, i = 1, 2, … , t.
Сравнения х а i (mod m i), i = 1, 2, … , t, имеют в интервале
[0, M – 1] единственное общее решение
х = a i • N i • М i (mod M).
Рассмотрим частный случай. Пусть М = m1 • m2 , где m1 и m2 – взаимно простые числа. Тогда для произвольных целых а1 < m 1 и а 2 < m 2 существует единственное число х, х < М, такое, что
х а 1 (mod m 1) и х а 2 (mod m 2).
Чтобы найти значение решения х, сначала используют алгоритм Евклида для вычисления значений N 1 и N 2 , таких, что
М 1 • N 1 1 (mod m 1) и М 2 • N 2 1 (mod m 2).
Здесь M m 1 • m 2 M
M 1 = = = m 2 ; M 2 = = m 1.
m 1 m 1 m 2
Затем вычисляют значение
х = (a 1 • N 1 • М 1 + a 2 • N 2 • М 2 ) (mod M).
Пример. Решить систему из двух сравнений
х 1 (mod 5),
х 10 (mod 11)
и найти общее решение х по модулю 55.
Здесь: m 1 = 5; m 2 = 11; M = m 1 • m 2 = 5 • 11 = 55;
а 1 = 1; а 2 = 10; M 1 = М / m 1 = m 2 = 11; M 2 = М / m 2 = m 2 = 5.
Найдем значения N 1 и N 2, обратные к M 1 и M 2 сответственно по mod m 1 и mod m 2 :
М 1 • N 1 1 (mod m 1), 11 • N 1 1 (mod 5) N 1 = 1,
М 2 • N 2 1 (mod m 2), 5 • N 2 1 (mod 11) N 2 = 9.
Вычислим общее значение
х = (a 1 • N 1 • М 1 + a 2 • N 2 • М 2 ) (mod M) =
= (1 • 11 • 1 + 10 • 5 • 9 ) (mod 55) = (11 + 450) (mod 55) =
= 461 (mod 55) = 21 (mod 55).
Итак, х = 21 (mod 55).
5.2 Кодирование
5.2.1 Оптимальное кодирование
Оптимальным кодированием называется процедура преобразования символов первичного алфавита m1 в кодовые слова во вторичном алфавите m2, при котором средняя длина сообщений во вторичном алфавите имеет минимально возможную длину.
Коды, представляющие первичные алфавиты с неравномерным распределением символов, имеющие среднюю минимальную длину кодового слова во вторичном алфавите, называются оптимальными неравномерными кодами (ОНК).
Эффективность ОНК оценивают при помощи двух коэффициентов:
1. коэффициента статического сжатия
,
который характеризует уменьшение количества двоичных знаков на символ сообщения при применении ОНК по сравнению с применением методов нестатистического кодирования.
2. коэффициента относительной эффективности
,
который показывает, насколько используется статическая избыточность передаваемого сообщения.
Из свойств оптимальных кодов вытекают принципы их построения:
выбор каждого кодового слова необходимо производить так, чтобы содержащееся в нем количество информации было максимальным,
буквам первичного алфавита, имеющим большую вероятность, присваиваются более короткие кодовые слова во вторичном алфавите.
Принципы оптимального кодирования определяют методики построения оптимальных кодов.
Построение ОНК по методике Шеннона-Фано для ансамбля из M сообщений сводится к следующей процедуре:
множество из M сообщений располагают в порядке убывания вероятностей;
первоначальный ансамбль кодируемых сигналов разбивают на две группы таким образом, чтобы суммарные вероятности сообщений обеих групп были по возможности равны;
первой группе присваивают символ 0, второй группе символ 1;
каждую из подгрупп делят на две группы так, чтобы их суммарные вероятности были по возможности равны;
первым подгруппам каждой из групп вновь присваивают 0, а вторым - 1, в результате чего получают вторые цифры кода. Затем каждую из четырех подгрупп вновь делят на равные (с точки зрения суммарной вероятности) части и т. д. До тех пор, пока в каждой из подгрупп останется по одной букве.
Функция Med находит медиану указанной части массива Р [b..e], т.е. определяет такой индекс m (b ≤ m < e), что сумма элементов Р [b..m] наиболее близка к сумме элементов Р [m + 1..e].
Примечание. При каждом удлинении кодов в одной части коды удлиняются нулями, а в другой части – единицами. Таким образом, коды одной части не могут быть префиксами другой. Удлинение кода заканчивается тогда и только тогда, когда длина части равна 1, то есть остается единственный код. Таким образом, схема построения префиксная, а потому разделимая, т.е. коды не требуют разделителя.
Пример: Построим оптимальный код сообщения, состоющего из восьми равновероятных букв.
Решение. Так вероятности данного ансамбля сообщений равны p1 = = p2 = ...= p8 = 2-3 и порядок их расположения не играет роли, то расположим их так, как показано в таблице 2.1.1. Затем разбиваем данное множество на две равновероятные группы. Первой группе в качестве первого символа кодовых слов присваиваем 0, а второй - 1. Во второй колонке таблицы записываем четыре нуля и четыре единицы. После чего разбиваем каждую из групп еще на две равновероятные подгруппы. Затем каждой первой подгруппе присваиваем 0, а второй - 1 и записываем в третью колонку таблицы. Далее каждую из четырех подгрупп разбиваем на две равновероятные части и первой из них присваиваем 0, а второй - 1. Таким образом в четвертой колонке появится значение третьего символа кодовых слов.
Таблица 5.4 – Оптимальный код равновероятных букв
Буква |
Кодовое слово полученное после разбиения |
||
|
первого |
второго |
третьего |
А1 А2 А3 А4 А5 А6 А7 А8 |
0 0 0 0 1 1 1 1 |
0 0 1 1 0 0 1 1 |
0 1 0 1 0 1 0 1 |
Проверка оптимальности кода осуществляется путем сравнения энтропии кодируемого (первичного) алфавита со средней длиной кодового слова во вторичном алфавите.
Для рассматриваемого примера энтропия источника сообщений
H = log2 N = log2 8=3 бит/символ
а среднее число двоичных знаков на букву кода
бит
где li - длина i-ой кодовой комбинации; pi - вероятность появления i-го символа комбинации длиной в li.
Таким образом, H = L, т. е. код является оптимальным для данного ансамбля сообщений.
Вывод: Для ансамблей равновероятных сообщений оптимальным является равномерный код. Если число исходных элементов ансамбля равно целой степени двух, то всегда H = L.
Пример. Первичный алфавит состоит из 8 символов со следующими вероятностями появления: a1 = 0,5; a2 = 0,25; a3 = 0,098; a4 = = 0,052; a5 = 0,04; a6 = 0,03; a7 = 0,019; a8 = 0,011. Построить ОНК по методу Шеннона - Фано и подсчитать коэффициенты.
Решение проиллюстрируем в таблице 5.5.
Таблица 5.5 – Оптимальный код неравновероятных букв
ai |
pi |
Кодовое слово после разбиения |
Знаков |
lipi |
|||||
|
|
1 |
2 |
3 |
4 |
5 |
6 |
|
|
1 |
0,5 |
0 |
- |
- |
- |
- |
- |
1 |
0,5 |
2 |
0,25 |
1 |
0 |
- |
- |
- |
- |
2 |
0,5 |
3 |
0,098 |
1 |
1 |
0 |
0 |
- |
- |
4 |
0,392 |
4 |
0,052 |
1 |
1 |
0 |
1 |
- |
- |
4 |
0,208 |
5 |
0,04 |
1 |
1 |
1 |
0 |
- |
- |
4 |
0,16 |
6 |
0,03 |
1 |
1 |
1 |
1 |
0 |
- |
5 |
0,15 |
7 |
0,019 |
1 |
1 |
1 |
1 |
1 |
0 |
6 |
0,114 |
8 |
0,011 |
1 |
1 |
1 |
1 |
1 |
1 |
6 |
0,066 |
Недостатком методики Шеннона – Фано является неоднозначность построения ОНК. В методике Хаффмена этого недостатка нет.
ІІ. Хаффмен предложил следующий метод построения ОНК:
Символы первичного алфавита выписываются в порядке убывания вероятностей.
Последние n0 символов, где 2 n0 m и N - n0 / m - 1 - целое число, объединяют в некоторый новый символ с вероятностью, равной сумме вероятностей объединяемых символов.
Последние символы с учетом образованного символа вновь объединяют и получают новый, вспомогательный, символ.
Опять выписывают символы в порядке убывания вероятноьстей с учетом вспомогательного символа и т. д. До тех пор, пока вероятности m оставшихся символов после N - n0/m - 1-го выписывания не дадут в сумме 1.
На практике обычно не производят многократного выписывания вероятностей символов, а обходятся элементарными геометрическими построениями, суть которых для кодов с числом качественных признаков m = 2 сводится к тому, что символы кодируемого алфавита попарно объединяются в новые символы, начиная с символов, имеющих наименьшую вероятность, а затем, с учетом вероятностей вновь образованных символов, опять производят попарное объединение символов с наименьшими вероятностями и таким образом строят двоичное кодовое дерево, в вершине которого стоит символ с вероятностью 1.
П ример.
Построить методом Хаффмена оптимальный код для алфавита со следующим распределением вероятностей появления букв в тексте: A = 0,5; B = 0,15; C = 0,12; D = 0,1;
E =0,04; F = 0,04; G = 0,03;
H = 0,02.
Решение.
Сначала находят буквы с наименьшими вероятностями 0,02 (H) и 0,03 (G), затем проводят от них линию к точке, в которой вероятность появления буквы G равна 0,05. Затем берут две наименьшие вероятности 0,04 (F) и 0,04 (E) и получают новую точку с вероятностью 0,08.
Теперь наименьшими вероятностями обладают точки, соответствующие вспомогательным символам с вероятностями 0,05 и 0,08. Соединяем их линией с новой точкой, соответствующей вспомогательному символу с вероятностью 0,13.
Продолжаем алгоритм до тех пор, пока линия от основных и вспомогательных символов не сольются в точке, дающую суммарную вероятность, равную 1.
Обозначим каждую верхнюю линию (см. рисунок 2.1.1) цифрой 1, а нижнюю - цифрой 0. Получим ОНК, который для каждого слова представляет собой последовательность нулей и единиц, которые встречаются по пути к данному слову от конечной точки (1,00).
Полученные коды представлены в таблице 5.6.
Таблица 5.6 – Двоичный код Хаффмена для восьми сообщений
Буква |
Вероятность |
ОНК |
Число знаков в кодовом слове |
pili |
A B C D E F G H |
0,50 0,15 0,12 0,10 0,04 0,04 0,03 0,02 |
1 0 0 1 0 1 1 0 1 0 0 0 0 1 1 0 0 0 1 0 0 0 0 0 1 0 0 0 0 0 |
1 3 3 3 5 5 5 5 |
0,50 0,45 0,36 0,30 0,20 0,20 0,15 0,10 |
Пример.
Построить код Хаффмена для передачи сообщений при помощи трех частот f1, f2, f3, если символы первичного алфавита встречаются в сообщениях со следующими вероятностями: А = 0,24; Б = 0,18; В = 0,38;
Г = 0,1; Д = 0,06; Е = 0,02; Ж = 0,02.
Решение.
Таблица 5.7 – Троичный код Хаффмена для семи сообщений
Буква |
Вероятность |
Дерево |
Код |
В А Б Г Д Е Ж |
0,38 0,24 0,18 0,1 0,06 0,02 0,02 |
|
f1 f2 f3f1 f3f2 f3f3f1 f3f3f2 f3f3f3 |
Полученный код легко декодируется, так как ни один код не начинается с f1 и f2, кроме одного одноразрядного кода.
К недостаткам алгоритма относятся:
Необходимость при кодировании двукратного прочтения файла первый раз для подсчета частоты вхождения символов,
второй – непостредственно для кодирования.
Необходимость хранения вместе с сжатым файлом декодирующего дерева для возможности восстановления файла.