Титры к видео уроку - "Основы DDL."

Ссылка на полный видео урок

Здравствуйте, сегодня мы будем рассматривать язык описания данных и говорить о целостности и непротиворечивости данных, которые находятся в наших БД. Первое что мы рассмотрим это язык описания данных. На прошлом уроке мы рассматривали язык манипулирования данными, который нам позволял выбирать данные из таблиц, изменять их, удалять и вставлять новые данные. Сегодня будем рассматривать язык описания данных, то есть это язык, который используется для определения и описания структур наших БД. В DDL входят такие операторы как CREATE, ALTER и DROP, которые позволяют создавать новые объекты БД, изменять существующие и удалять так же существующие объекты БД. Функции языка DDL определяются первым словом в предложении, которое почти всегда является глаголом. Это превращает природу языка в ряд обязательных утверждений к БД. Создай, измени и удали. Я думаю у вас не будет возникать никаких проблем с этим языком. Когда мы перейдем к примерам вам сразу же станет ясно как пользоваться языком описания данных. Теперь давайте поговорим о целостности и непротиворечивости данных БД. Созданные нами таблицы широко открыты для пользователей. Это значит, что пользователи могут записывать в таблицу любые данные, даже если они заведомо неверные. Единственное что может им помешать это типы данных. Пользователь, например, не сможет записать свое имя в поле типа BigInt, которое предназначено для хранения количества единиц продукции на складе. Но пользователь сможет записать свое имя например в поле для хранения номера телефона или же записать адрес проживание в поле для электронного адреса. Такие ошибки разрушают логическую структуру БД, где данные хранимые в ней заведомо неправильные. Нужно уметь каким то образом ограничить данные, которые вводит пользователь. Процесс ограничения данных называется процессом целостности данных. Целостность БД – это свойство БД, которое обеспечивает корректность и непротиворечивость данных в любой момент времени. Непротиворечивость БД говорит о том что в нашей БД нельзя будет найти два объекта, которые противоречат друг другу. Понятное дело, что целостность БД не гарантирует достоверности содержащейся в ней информации. Но обеспечивает по крайней мере правдоподобность этой информации, отвергая заранее неверные либо ложные значения. Целостность обеспечивается ограничением на вводимые пользователем данные. Всего существует 3 типа целостности данных: доменная целостность, это целостность сущностей и ссылочная целостность. Все виды целостности БД мы рассмотрим в нашей презентации. И начнем мы с доменной целостности. Сперва давайте дадим определение домену, которое можно встретить в теории БД.

Доменом в БД называется ограниченная допустимое подмножество значений заданного типа. Давайте к примеру рассмотрим домен «Имена». Имена в SQL-SERVER могут представлять строковое типы данных. Но в множество строковых значений существует ограниченное допустимое подмножество которые могут представлять именно «Имена». В частности, для возможности представления русских имен такие строки не могут начинаться с мягкого или твердого знака и не могут быть длиннее 20-ти символов.Таким образом доменная целостность гарантирует наличие в некотором столбце только допустимых значений. Этот тип целостности можно задать ограничением на проверку или ограничением на умолчание, то есть ограничением CHECK или DEFAULT. Ограничение на проверку, то есть ограничение CHECK используется для ограничения данных, принимаемых полем, даже если они не имеют корректный тип. Ограничение по умолчанию допускают пустые значения. Мы более подробней рассмотрим это в практических примерах к этому уроку. Далее мы рассмотрим целостность сущностей. Целостностью сущностей называется обеспечение гарантии уникальности записи в таблицах и предотвращение их дублирования. Представьте себе, если имя одного и того же клиента повторяется дважды в таблице Customers дублируя таким образом данные. Понятно что это будет не очень хорошо, у нас будет один клиент с двумя идентификационными номерами или же предположим что наш менеджер случайно ввел два клиента с одним идентификатором. Это может создать большие проблемы при продажах или генерировании отчетов поскольку мы не будем знать кто из клиентов делал покупки. Оба они выводятся как один. Такую проблему позволяют решить ограничения первичного ключа и на уникальность. В презентации мы будем более подробно изучать предназначение первичного ключа. Первичный ключ используется для придания уникальности каждой записи в таблице. Предположим что в качестве первичного ключа вы определили поле CustomerID таблицы Customers, которая находится у вас в БД и предположим что в таблице уже находится клиент с идентификатором равным 1. Это у нас Иванов Иван Иванович. Если один из ваших пользователей попытается создать запись о клиенте с таким же номером, то он получит ошибку и обновление не будет выполнено поскольку значение CustomersID уже причислено в уникальном индексе первичного ключа. Если бы мы не использовали первичный ключ для нашей таблицы то наши менеджеры могли бы добавлять сколько угодно клиентов с одним и тем же идентификационным номером. К тому же первичный ключ предоставляет ссылки для связи с другими таблицами. Но об этом мы поговорим немного позже. Теперь давайте перейдем к ссылочной целостности. Ссылочная целостность БД гарантирует что нельзя создать запись в одной таблице, которая ссылается на несуществующую запись в другой таблице. Ссылочную целостность обеспечивает так называемое ограничение внешнего ключа, это ограничение задает столбец, который ссылается на ограничение Primary Key или же на ограничение другой таблицы. Для того что бы понять что собой представляет ссылочная целостность давайте себе представим БД в которой имеются две таблицы. Это таблица клиентов с именем Customers и таблица заказов с именем Orders. Понятное дело, что данные, которые находятся в этих таблицах связаны между собой, то есть явно что для этих таблиц потребуется обеспечить ссылочную целостность. То есть дать гарантию, что в таблице Orders невозможно будет создать заказ, который будет ссылаться на несуществующего клиента. Понятное дело что такое невозможно. У нас есть заказ но кто сделал этот заказ мы не понимаем. Поэтому нужно обеспечить ссылочную целостность. В терминологии SQL-SERVER обеспечение ссылочной целостности достигается путем связывания первичного ключа одной таблицы с внешним ключом другой таблицы. После создания такой связи SQL-SERVER будет сам следить за тем что бы нельзя было нарушить целостность ссылок. В нашем случае нельзя было добавить новый заказ, который ссылается на несуществующего клиента. Для того что бы создать такую связь мы на таблице Customers создали поле с ограничением первичного ключа, это поле ID. В таблице Orders мы создали поле с названием IdC с ограничением внешнего ключа и мы указали что внешний ключ будет ссылаться на поле первичного ключа таблицы Customers. Тем самым уже отпадает возможность создания заказов, которые касаются несуществующих клиентов. И теперь давайте перейдем к примерам и более подробно рассмотрим что собой представляет язык описания данных и что собой представляют различные ограничения. В первом практическом примере к нашему уроку мы будем использовать язык описания данных для создания, изменения и удаления базы данных. Давайте откроем этот пример.

На предыдущих уроках мы с вами создавали базу данных ShopDB. Давайте сперва попробуем её удалить а потом заново создать. Удалять объекты можно с помощью оператора DROP языка описания данных. То есть на 7-й строке мы указываем оператор DROP и тем самым мы хотим удалить данную БД. Давайте выполним 7-ю строку тем самым удалим нашу БД ShopDB. Теперь давайте её попробуем заново создать. Для этого воспользуемся оператором CREATE это так же составная часть языка описания данных. Мы указываем что будем создавать БД с именем ShopDB. В опциях ON и LOG ON мы указываем параметры файловой группы для первичного файла нашей БД и для журнала транзакций. Наша БД будет находится на диске D в файле Shopdb.mdf и журнал транзакция в файле D:\LogShopdb.ldf . Также мы указали параметр размера нашей БД, параметр максимального размера и параметр прирощения. Такие же параметры мы указали для журнала транзакций. Давайте выполним с 14-й по 31-ю строки и тем самым создадим нашу БД. Если мы зайдем в Object Explorer и обновим каталог DataBases нашего сервера то мы увидим что действительно такая БД была создана. Удалять и создавать БД мы уже можем. Кстати, более подробное рассмотрение создания БД у нас было на первом уроке. Вы можете вернуться и посмотреть это видео и вспомнить более подробней как создается БД. Теперь давайте попробуем изменять нашу БД. После размещения БД и заполнения её пользовательскими данными вам потребуется изменить её размеры, то есть увеличить её или уменьшить. Если созданная вами БД становится более популярной нежели вы ожидали и пользователи добавляет новые данные то вам потребуется увеличить её размер. Для того что бы изменить параметры файла нашей БД мы будем пользоваться оператором ALTER.

На 39-й строке мы хотим изменить БД Shopdb, модифицировать файл нашей БД и дать новый размер. Когда мы создавали её мы указывали что размер БД должен быть 10 мб. Сейчас мы хотим увеличить размер нашей БД до 100мб. Давайте выполним 37-ю строку и с помощью процедуры sp_helpdb посмотрим информацию о БД Shopdb. Выполняем 37-ю строку и можем смотреть подробную информацию о нашей БД. Во второй табличке, которая есть у нас в окошке вывода мы можем видеть что первичный файл нашей ДБ имеет размер 10мб и максимальный размер 100 мб. Давайте выполним с 39-й по 43-ю строку и тем самым мы хотим изменить размер нашей БД. Выполняем скрипт, все у нас успешно было выполнено и давайте выполним еще раз 37-ю строку. Теперь мы видим что мы увеличили размер БД, было 10мб а стало 100мб. Теперь давайте еще раз изменим файл нашей БД. У нас теперь начальный размер равен максимальному по этому давайте модифицируем файл БД и увеличим максимальный размер БД. На 45-й строке, используя операцию ALTER мы будем изменять БД. Мы будем модифицировать файл, укажем новый размер файлу в 1000 мб и так же укажем новое значение увеличение размера файла БД. Давайте попробуем выполнить код. Видим что команды успешно выполнены. Выполняем на 37-ю строку и видим текущее состояние БД. Видим что размер остался 100 мб а максимальный увеличился. Теперь наша БД может занимать 1 Гб памяти на жестком диске. Давайте еще раз модифицируем файл нашей БД и уменьшим максимальный размер. Давайте выполним с 53-й по 59-ю строку. Теперь мы будем уменьшать максимальный размер до 10-ти Мб. Мы пробуем выполнится и у нас появляется ошибка, которая говорит, что то значение, которое мы хотим установить оно меньше текущего размера. Так делать нельзя. На 61-й строке мы будем так же использовать оператор ALTER для изменения файла БД Shopdb. Мы хотим задать размер файла 100 мб. Кстати, Обратите внимание, что сейчас как раз размер нашей БД является 100мб. Если мы выполним с 51-й по 65-ю строку то так же будет ошибка. Потому как не разрешается задавать размер БД меньше или равный текущему. Если мы и хотим изменить файл и увеличить текущий размер то нам придеться указать хотя бы размер на 1 мб больше. Выполняем сейчас и видим что файл нашей БД был модифицирован. Во втором практическом примере мы будем использовать язык описания данных для создания, удаления и изменения таблиц. Давайте откроем второй пример, сперва давайте подключимся к БД Shopdb. Теперь давайте создадим в нашей БД табличку. На 8-й строке нам предлагают удалить табличку Customers. Но пока что это делать бессмысленно. На 11-й мы создаем эту табличку в БД Shopdb. Наша таблица будет иметь следующие поля. Это тип CustomerNo с автоинкриментом. Указывая автоинкримент мы указали 2 дополнительных параметра для него. Первый это начальное значение автоинкримента для этого поля, другой параметр указывает шаг автоинкримента, то есть каждый раз значение автоинкримента будет расти на 2. На 14-й строке мы создаем еще одно поле с именем CustomerName типа варчар на 25 символов, которое недопускает пустого значения. Так же мы определили поле Adress1, на 16-й строке мы создаем поле Adress2, при этом мы указываем новое для нас ключевое слово при определении этого поля. Ключевое слово DEFAULT , это ключевое слово позволяет задать значение по умолчанию для данных, которые будут находится в этом поле. То есть если пользователь будет заполнять табличку и для поля Adress2 не даст какого то значения, то есть будет оставлять пустое значение, то это поле будет автоматически заполнено Unknown. Есть еще несколько полей, можете посмотреть и разобраться с ними. Давайте выполним с 11-й по 25-ю строку. У нас была создана табличка для нашей БД. Теперь давайте удалим её и попробуем создать заново. Выполняем 27-ю строку. Далее еще раз создадим таблицу Customers. Но теперь будем её создавать со сжатием по строкам. SQL SERVER поддерживает сжатие строк для таблицы. Использование этой функции способствует сжатия данных внутри БД а так же уменьшению самой БД. Помимо экономии места сжатие данных позволяет повысить производительность потому как в запросах считывать меньше информации. К сожалению в экспресс версии эта функция недоступна поэтому у нас не получится создать табличку со сжатием по строкам. Можете узнать более подробней о этой функции, открыв msdn. Так же для того что бы более подробней узнать о сжатии строк в таблицах вы можете почитать статью «Реализация сжатия строк». Пока что давайте создадим нашу таблицу без сжатия по строкам. На 47-й строке давайте попробуем добавить в нашу таблицу одну строку и на 53-й выполнить запрос всех данных. Вот, видим что одна строка у нас была добавлена. Кстати, обратите внимание что на 50-й при создании строки мы используем функцию GETDATE, эта функция позволяет получить текущую дату и время. Теперь давайте попробуем изменять нашу таблицу. Для этого используем оператор ALTER. Сперва давайте давайте изменим нашу табличку и предоставим новый столбец.

На 63-й строке мы указываем что хотим изменить таблицу Customers, на 64-й строке мы указываем ключевое слово ADD и указываем что хотим добавить новый столбец в нашу таблицу, типа Int значения NULL. Давайте выполним с 63-й по 66-ю строку и выберем все данные из таблицы Customers и видим что у нас появился новый столбец и в нем значение NULL. Теперь давайте поменяем нашу таблицу и удалим то поле, которое мы с вами добавили. На 75-й строке мы изменяем таблицу Customers, на 76-й указываем что хотим удалить столбец с именем NewFild . Выполняем с 75-й по 82-ю строки. И тем самым удаляем это поле. На 80-й строке производим выборку из таблицы Customers но у нас его нет, потому как мы его уже удалили. Теперь давайте создадим еще одно поле для нашей таблицы, поле с именем NesField2 типа VarChar на 20 символов, которое не позволяет пустых значений. Выполним с 80-й по 87-ю строки и видим ошибку, которая говорит о том что мы хотим в поле, которое не допускает NULL записать пустые значения. Ну это действительно так потому что у нас уже есть пустая строка в таблице, которая заполнена если мы добавим еще одно поле к таблице то это поле нашей строки будет иметь значение NULL но мы противоречим сами себе так как в самом начале мы указали что поле не может содержать пустых значений. Если мы все таки захотим добавить поле, которое не может содержать значений NULL то нам понадобится установить значение поля по умолчанию. На 89-й строке мы изменяем таблицу Customers, добавляем новое поле с именем NewField2 типа VarChar на 10 символов и указываем на недопустимость пустых значений. На 92-й строке мы используем ключевое слово DEFAULT. Мы указываем что значение по умолчанию для этого поля «Unknown». То есть все поля, которые мы хотим оставить пустыми будут принимать значение «Unknown». Давайте выполним с 89-й по 93-ю строку – мы добавили новое поле, которое не допускает пустых значений. И на 95-й строке давайте попробуем выполнить поиск всех данных в таблице. Мы видим что строка у нас осталась, к ней было добавлено новое поле и оно заполнено по умолчанию значением «Unknown». В третьем примере мы с вами научимся пользоваться ограничением первичного ключа. Мы помним что это ограничение обеспечивает целостность сущностей. Целостность сущностей гарантирует уникальность записей в таблицах и предотвращение их дублирования. Сперва нам предлагают подключится к БД Shopdb и удалить табличку Customers. На 18-й строке мы хотим создать табличку Customers у которой будет шесть полей. Поле CustomerNo типа Int не допускающее значений NULL. На это поле мы указываем ограничение первичного ключа. Это делается с помощью указания Primary Key первичного поля.

На 19-й строке мы создаем поле CustomerName , дальше – Adress1, City, Contacts и Phone. Давайте создадим нашу табличку Customers. Мы видим что наша табличка имеет первичный ключ. Ограничение с полем ключа недопускает неуникальных значений. Давайте в этом убедимся. На 27-й строке, используя оператор INSERT языка манипулирования данными мы вставляем 2 строки в таблицу. Вставляем строку «Петренко Петр Петрович » и строку «Иваненко Иван Иванович». Первая строка имеет идентификатор 1, второй клиент имеет идентификатор2, то есть данные, которые будут находится в поле CustomerNo нашей таблицы не будут дублироваться, поэтому у нас будет вставлено две строки в нашу табличку. Теперь давайте добавим еще одну строку в табличку и попробуем нарушить уникальность для поля CustomerNo. 35-я строка вставляем еще одно поле в табличку «Сидоров Семен Семеныч» у которого идентификационный номер 1. Мы установили для поля CustomerNo первичный ключ по этому теперь наш SQL SERVER будет следить за тем что бы мы не нарушили уникальность. Мы хотели её нарушить но у нас не получилось. Давайте на 40-й строке выберем все из таблицы Customers. У нас есть только «Петренко Петр Петрович» и «Иваненко Иван Иванович». Теперь удалим табличку Customers и попробуем создать её заново только так что бы в табличке был составной первичный ключ. Дело в том что первичный ключ в табличке может быть только один но возможно создавать составной первичный ключ. Этот первичный ключ будет состоять из значений нескольких полей. Тем самым теперь ограничение на уникальность будет устанавливаться не отдельно для каждого столбца из которого состоит первичный ключ а для пар значений. Давайте рассмотрим этот пример.

Мы создаем табличку в которой есть 6 полей на последней строке которой мы создаем псоставной первичный ключ для нашей таблицы. Наш составной ключ будет состоять из двух полей CustomerNo и CustomerName. Теперь SQL-SERVER будет следить за уникальностью двух полей CustomerNo и CustomerName. Если уникальность этих двух значений будет нарушена то нельзя будет вставить новую запись в таблицу. Давайте посмотрим на 61-ю строку. Вставляем данные в табличку Customers , вставляем две строки одну «Петренко Петр Петрович » и две строки «Иваненко Иван Иванович». Пробуем вставить эти строки. У нас уникальность не будет нарушена поэтому в таблице появится две записи. 68-я стрка- мы хотим вставить еще одну строку в таблицу Customers. Это следующая строка (1) «Сидоров Семен Семенович». Давайте попробуем вставить эту строку. Эта строка была вставлена хотя это значение не уникально. У нас есть 2 одинаковых значения (1). Дело в том что наш первичный ключ гарантирует уникальность только пары значений CustomerNo и CustomerName. То есть у нас есть (1) «Петренко Петр Петрович» и (1) «Сидоров Семен Семенович». Видите уникальность первичного ключа не нарушена. Вот если бы мы добавляли второго (2)«Петренка Петра Петровича» с идентификатором (1) тогда была бы ошибка. Давайте попробуем выполнить с 68-й строки по 71-ю, я уже выполнял поэтому у меня ошибка. Теперь давайте перейдем на 73-ю строку и мы хотим добавить новую строку в таблицу Customers, хотим добавить Иваненка Ивана Ивановича с идентификационным номером (2). У нас этого сделать не получится потому что у нас уже есть Иваненко Иван Иванович с идентификационным номером 2. При попытке вставить эту строку в таблицу мы нарушим ограничение уникальности первичного ключа. Теперь выполним 78-ю строку и посмотрим что всего у нас было вставлено 3 строки в таблицу. Это (1)«Петренко Петр Петрович», (1) «Сидоров Семен Семенович» и (2) Иваненко Иван Иванович. Теперь давайте попробуем удалить нашу таблицу и создать её заново без каких либо ограничений и потом с помощью оператора ALTER языка описания данных мы попробуем добавить для нашей таблицы ограничение. Выполняем 81-ю строку. Мы удалили таблицу. Создаем таблицу заново на 84-й строке будет иметь также 6 знакомых нам полей. Обратите внимание что никаких ограничений у нас нет на нашей таблице. На 96-й строке мы хотим изменить таблицу и добавить новое ограничение для нашей таблицы. Это ограничение будет ограничение первичного ключа и это ограничение будет касаться только поля CustomerNo нашей таблички. Обратите внимание что на 97-й строке нашему ограничению мы даем имя PK_Customers это нужно для того чтобы потом можно было обратится к этому ограничению и его удалить. Давайте выполним с 96-й по 98-ю строку. Наш оператор отлично сработал и теперь это говорит о том что теперь есть ограничение первичного ключа на поле CustomerNo. Теперь давайте попробуем вставить данные в таблицу Customers. Теперь мы не будем указывать явные значения Customers при вставке новых записей потому как при создании таблицы первое поле является автоинкрементировано. Давайте выполним с 100-й по 105-ю строку. У нас было добавлено 2 строки в нашу таблицу. Давайте выполним вывод всех данных из таблицы Customers. Производим поиск. У нас есть Петренко Петр Петрович с идентификатором (1) и Иваненко Иван Иванович с идентификатором (2). Теперь давайте удалим табличку еще раз, создадим её заново и создадим для этой таблички ограничение первичного ключа для двух полей, то есть составной ключ. 123-я строка – изменяем табличку Customers и задаем ограничение без имени. Указывать имя ограничения необязательно, но просто потом мы не сможем к нему обратится. 123-я строка- изменяем табличку Customers, добавляем Primary Key, то есть ограничение первичного ключа для столбцов CustomerNo и Adress1 нашей таблички. Мы создали составной ключ таблички и теперь хотим создать две строки. (1) «Петренко Петр Петрович, луганская 25» и (2) «Иваненко Иван Иванович, Дихтяревская 5». Выполняем с 127-й по 132-ю строку и у нас было добавлено 2 записи в таблицу Customers. 134-я строка – добавляем еще одну запись. Мы хотим добавить «Сидоров Семен Семенович, Драйзера 12» и наш клиент будет иметь идентификационный номер (1). Выполняем 134-137 строки. Так же – строка была добавлена потому как мы не противоречим тому ограничению, которое создали. То есть мы должны гарантировать уникальность пар значений CustomerNo и Adress1и мы можем увидеть что эти значения у нас уникальны. (1) Драйзера 12 и (1) Луганская 25. Теперь давайте на 139-й строке добавим еще одну строку в таблицу Customers. Это строка клиента Иваненка Ивана Ивановича, который проживает на Янгеля 32. При этом идентификатор у нашего клиента будет (2). Выполняем с 139-й по 142-ю строки. Добавили одного клиента. Так же мы не противоречим ограничению. И выполняем 144-ю строку и у нас есть 4 клиента в таблице Customers. Если мы захотим добавить еще одного, «Иваненко Ивана Ивановича» с ид-номером (2), который живет по адресу Янгеля 32 то у нас ничего не получится. У нас будет противоречие нашему составному первичному ключу таблицы Customers.

Четвертый пример. В четвертом примере мы рассмотрим как пользоваться ограничением внешного ключа для обеспечения ссылочной целостности БД. Давайте откроем пример 004_Foreign_Key. Перейдем на первую строку и сперва подключимся к БД Shopdb. Теперь давайте удалим табличку Customers, которая уже должна быть в нашей БД и создадим её заново. На 7-й строке мы создаем табличку Customers у которой есть поля CustomerNo, CustomerName, Adress1, City, Contacts и Phone. При этом обратите внимание что у нас CustomerNo это первое поле таблицы Customers – это поле с ограничением первичного ключа. При этом так же это поле с автоинкриментом то есть сервер сам будет сам будет заполнять это поле. Давайте создадим эту табличку. Выполняем с 7-й по 17-ю строку и табличка была успешно создана. Теперь давайте создадим еще одну табличку, которая будет связана с табличкой клиенты. Эту табличку мы назовем Orders (Заказы). Понятное дело что каждому заказу должен соответствовать какой то клиент. Создание такой таблички находится на 31-й строке. В этой таблице у нас будут 4 поля: OrderID, CustomerNo, OrderDate и Goods. OrderID это поле первичного ключа таблички, оно указывает на идентификатор заказа. Это поле у нас будет с автоинкриментом. Теперь нам нужно как то связать табличку Orders с табличкой Customers. Мы создаем поле CustomerNo в табличке Orders. Это поле будет указывать на идентификатор клиента который относится к тому или иному заказу. К тому же для обеспечения ссылочной целостности мы будем устанавливать ограничение внешнего ключа. Давайте посмотрим как создается это ограничение. На 36-й строке мы указываем дополнительный параметр, то есть указываем ограничение для поля CustomerNo. Мы указываем что это поле будет с ограничением Foreign Key, который ссылается на CustomerNo таблички Customers. При этом обратите внимание что первое поле CustomerNo таблички Customers это поле с ограничением первичного ключа, при этом это поле так же с автоинкриментом. На 37-й строке мы создаем так же поле OrderDate и поле Goods для таблички Orders. Указав ограничение внешнего ключа для этого поля сервер будет следить что бы мы не добавили заказ, который ссылается на несуществующего клиента. Давайте выполним с 31-й по 40-ю и тем самым создадим табличку Orders. Теперь давайте добавлять данные в табличку Customers и табличку Orders. Понятно что пока что мы не можем добавлять каких либо значений, каких либо строк в табличку Orders потому как каждый заказ должен быть закреплен за определенным клиентом но у нас пока что нет клиента, потому при попытке выполнить сначала вставку данных в таблицу Orders у нас будет ошибка, которая будет говорить о том что так делать нельзя. Поэтому давайте перейдем на 42-ю строку и сперва попробуем добавить данные в табличку Customers. Мы в табличку Customers добавляем информацию о двух клиентах – это Петренко Петр Петрович и Иваненко Иван Иванович. Давайте выполним с 42-й по 46-ю строку и две строки были добавлены в табличку Customers. Это мы видим в окошке вывода. Теперь мы можем создавать заказы для наших клиентов. Нам звонит клиент с идентификатором (1) и говорит что хочет заказать KeyBoard, дальше, звонит клиент с идентификатором (2), то есть Иваненко Иван Иванович и он заказывает у нас мышь и веб-камеру и так же клиент с идентификатором (1) у нас заказывает мышь. Давайте выполним строки с 48-й по 54-ю. Четыре новых строки были добавлены в табличку. Если мы захотим добавить строку в табличку Orders которая ссылается на клиента с несуществующим идентификационным номером то мы получим ошибку. Но сперва давайте посмотрим какие данные уже есть в табличке Customers и в табличке Orders. Выполняем 56-ю строку – это запрос на поиск данных из таблички Customers. У нас есть два клиента – это Петренко Петр Петрович с айди (1) и Иваненко Иван Иванович с айди (2). Значение ID для наших клиентов сервер выбрал сам с помощью автоинкримента. Давайте перейдем на 56-ю строку. Давайте еще посмотрим какие данные есть в таблице Orders. В таблице Orders у нас есть 4 заказа.

Переходим на 62-ю строку, давайте добавим в табличку Orders заказ, который ссылается на клиента (3). Такого клиента у нас нет, у нас есть клиенты только с айди (1) и (2). Потому как на таблице Orders существует ограничение внешнего ключа для CustomerNo то сервер будет следить для обеспечения ссылочной целостности таблицы Orders и Customers и просто на просто он не позволит вставить вот такую вот строку в таблицу. Давайте выполним с 62-й по 65-ю и мы получаем ошибку. Теперь давайте удалим табличку Orders. Давайте попробуем создать её заново но при создании мы не будем указывать ограничение внешнего ключа. Мы потом это ограничение добавим с помощью оператора ALTER языка описания данных. Давайте просто создадим табличку. Создали. И для поля CustomerNo мы не определили ограничение. Потому сейчас в табличку Orders можно вставлять любые заказы. Даже те заказы, которые ссылаются на несуществующих клиентов. Но давайте добавим к нашей таблице ограничение внешнего ключа. На 80-й строке используем оператор ALTER языка описания данный мы изменяем табличку Orders, к нашей табличке мы будем добавлять новое ограничение. Нашему ограничению мы дадим имя FK_Customers_CustomerNo, то есть мы даем имя с помощью которого можно потом найти это ограничение. И 82-я строка мы указываем тип ограничения и дополнительные параметры для ограничения. Мы указываем что наш внешний ключ будет касаться поля CustomerNo таблички Orders. После ключевого слова мы указываем тип и параметры ограничения. То есть мы указываем что наш внешний ключ будет касаться поля CustomerNo таблички Orders. Ключевым словом REFERENCES мы указываем на какое поле будет ссылаться после CustomerNo таблички Orders. CustomerNo таблички Orders. Выполняем с 80-й по 82-ю и видим что ограничение было добавлено в нашу таблицу. Давайте попробуем удалить табличку Customers. У нас не получается. А дело в том, что если есть связь между таблицами, то сервер не позволяет нам удалить родительскую таблицу. Родительская таблица это та, которая с первичным ключом, а дочерняя с внешним ключом. Мы хотим удалить таблицу родительскую и у нас не получается это сделать. Для того что бы можно было удалить табличку Customers то нам нужно сначала удалить связь этой таблицы с Orders. Если мы удалим сначала удалим табличку Orders то потом сможем удалить и табличку Customers потому что она не является родительской для других таблиц в нашей БД. Удаляем Customers. Теперь давайте перейдем к следюющему примеру и попробуем заново создать табличку Customers и Orders и добавить к ним ограничение. На 95-й строке мы создаем табличку Customers, указываем ограничение первичного ключа на поле CustomerNo этой таблички. Далее на 107-й строке мы создаем табличку Orders. В этой табличке у нас будет еще одно поле с первичным ключом – это поле OrderID. Врешнего ключа у нас пока что нет на этой таблице. Мы изменяем табличку Orders и добавляем новое ограничение с именем FK CustomersCustomerNo и указываем на 119-й строке что это ограничение внешнего ключа на поле CustomerNo нашей таблички Orders, это поле таблички Orders будет ссылаться на поле CustomerNo таблички Customers. Давайте создадим это ограничение. Создаю табличку Orders. Попробую изменить эту табличку и все успешно выполнилось. Зачем мы давали нашему ограничению имя. Мы говорили что имея имя мы сможем потом как то обратится к этому ограничению и что то с нима сделать. Вот давайте попробуем удалить ограничение внешнего ключа на табличке Orders. На 123-й строке используя оператор ALTER языка описания данных мы будем удалять ограничение FK CustomersCustomerNo. До удаления ограничения давайте попробуем удалить табличку Customers – у нас не получается потому как табличка Customers связана с табличкой Orders. Если мы удалим ограничение FK для таблички Orders то тогда можно будет удалять табличку Customers потому как она не связана с какими то данными из таблички Orders. Выполняем 127-ю строку и все у нас успешно удаляется.

Теперь давайте перейдем к следующему примеру и посмотрим как использовать каскадную ссылочную целостность. Открываем пример №5, в этом примере мы сперва подключимся к БД Shopdb. И потом создадим таблички для нашей БД с именами Customers и Orders. Эти те таблички, которае мы создавали в предыдущем примере. Сперва удаляем существующие таблички Customers и Orders и создадим их заново. На 8-й строке я создаю табличку Customers. В этой табличке есть поле CustomerNo с ограничением первичного ключа. Создаю табличку Customers и она успешно создалась. На 20-й строке я создаю табличку Orders в которой есть поле OrderID, которое является ограничением первичного ключа для этой таблицы. Так же есть поле CustomerNo, которое служит для того, чтобы совмещать данные из таблицы Orders с данными из таблицы Customers. ТО есть на самом деле это поле должно быть с ограничением первичного ключа но пока что оно без него. Дальше мы это ограничение добавим. Давайте пока что создадим табличку Orders и перейдем на 30-ю строку. На 30-й строке с помощью оператора ALTER описания данных мы будем добавлять к таблице Orders с ограничением внешнего ключа на поле CustomerNo. Это поле таблички Customers будет ссылаться на поле CustomerNo из таблицы Customers. Давайте создадим это ограничение тем самым мы обеспечили ссылочную целостность для таблиц Orders Customers. Теперь давайте перейдем на 34-ю строку. Найдем двух клиентов и вставим в таблицу клиентов. Выполняем с 34-й по 38-ю строку. Были добавлены Петренко Петр Петрович и Иваненко Иван Иванович. Теперь давайте добавим одну строку в таблицу Orders, то есть попробуем добавить один заказ. Добавили заказ на 45-й и 46-й строке мы попробуем выполнить запрос на вывод всех данным из табличек Customers и Orders. В табличке Customers у нас есть информация о двух клиентах а в табличке Orders у нас есть один заказ, которые у нас произвел клиент с ID(1), то есть клиент Петренко Петр Петрович. Давайте пойдем дальше и посмотрим что будет если мы захотим удалить клиента на котором весит заказ. На 49-й строке мы используя оператор DELETE мы будем удалять строку из таблицы Customers а именно клиента с именем Петренко Петр Петрович. Дело в том что есть заказ на него имя и когда мы захотим удалить его то нам выдаст ошибку. Так делать нельзя. То есть для этого клиента есть какие то дочерние записи. Как мы уже убедились мы не можем удалить запись в первичном ключе, то есть с присутствием записей в первичном ключе. Однако это поведение можно изменить используя каскадную ссылочную целостность.

Давайте перейдем к следующему примеру и посмотрим что это такое. Сперва давайте попробуем удалить ограничение FK_CustomersCustomerNo. На 66-й строке мы создаем такой запрос и удаляем ограничение внешнего ключа таблички Orders. Давайте перейдем к следующему примеру. Когда мы создаем внешний ключ для любой таблицы мы можем указать дополнительный параметр, который будет указывать правило для удаления или изменения родительских строк. Это правило для ON DELETE UPDATE. Мы изменяем табличку Orders, добавляем ограничение внешнего ключа на столбец CustomerNo, который будет ссылаться на строку CustomerNo таблички Customers. При этом мы указываем что при удалении строки с родительской таблицы нужно каскадно удалить все ссылающиеся строки из дочерней таблицы. Давайте это проверим выполняя с 76-й по 80-ю страницу. Давайте вспомним какие данные хранятся в табличке Customers и Orders. В Customers два клиента а в Orders один заказ. Давайте подумаем что будет если мы захотим удалить клиента Петренко Петра Петровича. Дело в том, что на этого клиента у нас ссылается один заказ. Потому как мы при создании первичного ключа указали ON DELETE CASCADE параметр – тем самым мы сказали что при удалении любого клиента на которого кто то ссылается то все ссылающиеся заказы нужно удалить. Давайте выполним 76-ю и 77-ю строку. У нас была обработана одна строка. Давайте посмотрим какие данные хванятся в наших табличках. В табличке Customers находиться только один клиент потому что другого мы удалили а в табличке Orders у нас был один заказ, но он удалился так как мы указали что при удалении нужно удалять каскадно все дочерние строки. Теперь давайте попробуем нашу БД вернуть в начальное состояние, то есть вернуть клиента и заказ. Для этого нам нужно будет его просто напросто добавить. Но проблема в том что для таблички Customers у нас указан автоинкримент. Если мы просто так добавим нового клиента в нашу таблицу то он будет с ID(3), но нам нужно чтобы он был со значением автоинкримента (0). Поэтому давайте обратимся к нашей таблице и укажеем что клиента нужно добавить с идентификатором (1). Для этого нужно использовать команду CheckIdent. Эта команда принимает три значения. Она находится на 82-й строке. Первое значения – для какой таблицы нужно изменить автоинкримент. Второе значение указывает что текущее значение автоинкримента должно изменится а последний параметр указывает на то, какое значение должно быть у автоинкримента. Мы выполняем 82-ю строку и тем самым указываем текущее значение автоинкримента 0 значит следующее значение будет (1). При вставке новой строки в табличку Customers Петренко Петр Петрович будет иметь идентификационный номер 1. Давайте перейдем на 90-ю строку и переведем автоинкримент в значение 2. Используем ту же функцию CheckIdent для той же таблицы и указываем что нужно вернуть значение автоинкримента 2. То же самое мы сделаем для таблички Orders. Собъем автоинкримент в ноль, добавим новую строку в табличку Orders и давайте выполним вывод всех данных с табличек. И посмотрим действительно ли они вернулись в первоначальное состояние. Видим чо это действительно так. Теперь давайте использовать другой параметр для обеспечения каскадной целостности для таблиц Orders и Customers. Давайте удалим старое ограничение первичного ключа на табличке Orders и укажем новое. Для нового мы укажем значение ON DELETE SET NULL. Это говорит о том что если мы захотим удалить из родительской таблицы строку на которую ссылаются. ТО во всех ссылающихся строках для поля с ограничение внешнего ключа нужно поставить значение NULL. Добавили новое ограничение на 117-й строке и теперь давайте попробуем удалить нашего клиента Петренко Петра Петровича. Я вам напоминаю, что на клиента ссылается один заказ. Пробуем удалить нашего кастомера и выполняем поиск по таблице Customers и Orders. Клиент с Id (1) у нас удалился. Заказ остался но теперь в поле заказа с ограничением внешнего ключа стоит значение NULL. То есть наш заказ остался, но «висит в воздухе», то есть не остался не за каким из наших клиентов.

Теперь давайте опять таки вернем наши таблицы в первоначальное состояние. Выполняем с 124-й по 144-ю строки. Выполняемся и выполняем 146-ю и 147-ю строку и видим что наша БД была возвращена в первоначальное состояние. У нас есть два клиента и один заказ. Давайте будем использовать еще одно правило для удаления записей родительской таблицы. Давайте удалим старое значение FK_CustomersCustomerNo и добавим новое с параметром ON DELETE SET DEFAULT. Этим мы указываем при удалении строки из родительской таблицы все дочерние строки поля с ограничением FK должны принимать свои значения по умолчанию. Если мы посмотрим на табличку Orders, которую мы создавали на 20-й строке то мы увидим что в поле CustomerNo стоит по умолчанию значение (2) и если мы будем удалять родительские строки то все строки из таблички Orders в поле CustomerNo будут иметь значение 2. Выполняем с 456-й по 160-ю строку, добавляем ограничение FK с параметром ON DELETE SET DEFAULTS. Давайте выполним 166-ю и 167-б строки и давайте запомним это значение CustomerNo со значением 1. Когда мы захотим удалить строку из таблички Customers то есть клиента Петра Петровича. То он у нас удаляется. И давайте теперь посмотрим какие данные остаются в табличке Orders. Первого клиента мы не видим и видите что заказ перешел ко второму клиенту с айди (2). То есть это мы сделали с помощью указания этого правила. При удалении указать значение по умолчанию. Давайте выполним со 169-й по 189-ю строку и вернем таблички в первоначальное состояние. Посмотрим вывод и видим что таблички вернулись. Так же у нас есть возможность установить правило NO ACTION (это значит ничего не делать). Если мы указываем NO ACTION то сервер просто напросто будет запрещать удалять данные из родительских строк на которых ссылаются строки из дочерних таблиц. 195-я строка мы удаляем ограничение FK CustomersCustomerNo таблички Orders. На 199-й создаем его заново используя ON DELETE NO ACTION. Вспоминаем что у нас есть табличка Customers и Orders и пробуя удалить строку из табличкиCustomers и у нас не получается. Если бы мы закомментировали ON DELETE NO ACTION то ситуация была бы такая же. Так как это параметр по умолчанию. Мы уже знаем как обеспечить ссылочную целостность и целостность сущностей наших БД. Но мы еще не научились обеспечивать доменную целостность.

Давайте перейдем к 6-му примеру и научимся это делать. Мы помним что доменная целостность гарантирует наличие в некотором столбце только допустимые значения. Давайте подключимся к БД Shopdb и давайте попробуем создать заново табличку Customers для нашей БД. Создаем её на 13-й строке. В ней будет шесть полей. Давайте определимся какие значения пользователь сможет записывать в поле с именем Phone. Поле с именем Phone имеет тип Char на 12 символов так что в принципе сможет записать любую строку не больше 12-ти символов в это поле. Строка не обязаьельно может быть номером телефона. Это может быть и адресом электронной почти, адресом сайта или адресом проживания, его имя или фамилия. Но мы хотим что бы пользователь записывал только номер телефона. Мы хотим из всего множества строк, которые будут занимать 12 символов определить некое подмножество, которое будет соответствовать шаблону, то есть пользователь должен вводить данные в это поле в следующем формате: Он должен открыть круглую скобку и дальше записать 3 цифры, это код оператора. Дальше он должен закрыть скобку и записать следующие 7 цифр его номера. То есть тем самым для поля Phone мы обеспечиваем доменную целостность. То есть мы позволим записывать в это поле только те значения, которые являются номером телефона. Конечно это не будет гарантировать достоверность информации, это не будет гарантировать что пользователь ввел правильный номер телефона, но это ограничение будет отвергать те значения, которые заведомо неверны, то есть это те значения, которые имеют символы латинского алфавита в строке.

Давайте создадим табличкуCustomers и попробуем добавлять данные в эту табличку. 25-я строка: клиент обращается в нашу БД и добавляет информацию о себе в эту табличку. Он указывает что его зовут Alex, он живет на улице NewSTR, имеет следующий e-mail адрес и записывает свой номер телефона. Мы используем ограничение Check. И тем самым эта строка должна успешно добавится в табличку Customers. Выполняем с 25-й по 28-ю строку. Одна строка была добавлена в табличку Customers. Теперь давайте представим, что другой клиент также хочет внести информацию о себе в табличку но он хочет внести неправильный номер телефона, например хочет его зашифровать. Он вставляет данные и номер телефона по следующему шаблону. В скобках указывает код оператора и вместо самого номера он указывает просто звездочки. У нас будет срабатывать ограничение Check для номера телефона, который проверит соответствует ли номер телефона шаблону: в круглых скобках 3 цифры и после них еще 7 цифр. Номер телефона на 33-й строке не соответствует шаблону поэтому когда мы захотим выполниться у нас будет ошибка. На 35-й строке давайте выполним поиск всех данных из таблички Customers. Выполнились и видим что только одна строка информации об одном клиенте была добавлена в таблицу. Теперь давайте удалим таблицу Customers на 37-й строке. Теперь давайте поставим еще одно ограничение для поля Phone.Как известно все номера телефонов у нас уникальны. Невозможно найти два одинаковых номера телефона. Давайте создадим табличку Customers и в поле ограничения укажем UNIQUE.Если два пользователя захотят вставить два одинаковых номера телефона то это у них просто не получится. Строка №40. Создаем табличку и в поле ограничения мы указываем её UNIQUE. Так же это ограничение называется еще альтернативным ключем. Давай выполним с 40-й по 49-ю строку. Таблица была создана. На строке 51 мы хотим добавить информацию о клиенте, у которого номер телефона (093)*******. Выполняем с 51-й по 54-ю строку. Информация была добавлена. Теперь давайте вставим еще одну строку в табличку Customers. Это клиент с номером телеофна (093)12312312. Выполняем с 56-й по 59-ю строку и еще одна строка была добавлена в нашу табличку. 61-я строка: выбираем все данные с таблицы и видим что действительно было добавлено два клиента. У них номера телефонов уникальны. Если мы зохотим вставить еще одного клиента с таким же номером телефона, ну давайте допустим тут поменяем на Tom. Том, который живет на NewStr2, в городе City с другим эл. Адресом и таким же номером телефона то у нас это не получиться потому что мы нарушим ограничение уникальности для поля Phone. И сообщение об этом мы увидим в окошке вывода. Мы нарушили ограничение с таким то именем: нельзя добавить дублирующийся альтернативный ключ и мы видим для какого значения мы хотели нарушить уникальность. Выбираем поиск всех данных и видим что осталось двое клиентов. Новый клиент не добавился. У нас нету Тома. Теперь давайте удалим табличку Customers, создадим её заново но теперь для поля Phone мы укажем одновременно два ограничения. То есть ограничения в поле Phone должны будут соответствовать шаблону, который мы укажем с помощью Check и так же номера телефонов должны будут быть уникальны. Создаем нашу табличку указывая два ограничения данных сразу же. И теперь давайте попробуем вставить данные в нашу табличку. На 79-й строке мы вставляем новую строку. Вставили. номер телефона этого клиента уникален потому никакой ошибки не было. 84-я строка: пробуем вставить информацию о клиенте, который неправильно указал свой номер телефона, который не соответствует шаблону. Получаем ошибку. Пробую вставить еще одного клиента, который дублирует уже существующего клиента. Пробую выполнить и не получается. Опять таки нарушаем ограничение UNIQUE. На 84-й мы нарушили ограничение Check, на 89-й ограничение UNIQUE. Выполняем поиск всех данных таблички Customers и получаем одну строку. Теперь давайте создадим табличку без ограничений и потом с помощью оператора ALTER языка описания данных добавить ограничение для нашей таблицы. С 99 по 108-ю строки мы создаем нашу табличку без ограничений для поля Phone. Дальше, 112-я строка, используя ALTER мы добавляем ограничение с именем CN_CustomersPhoneNo для таблички. Мы используем ограничение Check для поля Phone. То есть телефон должен соответствовать шаблону, который мы указали на 115-й строке. Указываем ограничение Check. На 118-й строке пробуем добавить нового клиента. У него номер телефона соответствует шаблону потому он дабавляется. 123-я строка, поле не соответствует шаблону потому строка не добавляется. Появляется ошибка. Когда мы создаем ограничение для таблички с помощью оператора ALTER мы даем нашему ограничению какое то имя. Потом мы може обратится к нему и что то с ним сделать. В случае с ограничением Check мы можем его отключить. Давайте посмотрим как это сделать. 130-я строка мы изменяем табличку Customers, отключаем ограничения с именем CN_CustomersPhoneNo. Можно будет вставлять новых клиентов, номера телефонов которых не соответствуют шаблонам. Давайте попробуем это сделать. У которого номер телефона (093)******* не соответствует шаблону. Но он добавляется так как мы отключили это ограничение на время. Давайте попробуем его включить. Строка №40 – изменяем табличку Customers. Включаем ограничение с именем CN_CustomersPhoneNo. Выполняем 140-ю и 141-ю строки. И 144-я строка пробуем вставить клиента, номер телефона которого не соответствует шаблону. Этого сделать не получается потому как уже работает ограничение. Теперь давайте попробуем удалить ограничение и потом его включить. Строка №150: изменяем табличку Customers, удаляем ограничение и пробуем вставлять данные. Ограничение удалено, оно не работает поэтому можно вставлять данные, которые не соответствуют шаблону. Но если ограничение мы уже удалили то включить его не получится потому как его нет. 160-я строка. Изменяем табличку Customers и пробуем включить ограничение. Выполняемся и сделать этого не получается. Давайте вернемся к презентации и рассмотрим различные виды связей между таблицами. Ну я думаю дать определение понятию «Связи» для нас уже не проблема. Связь – это некоторая ассоциация между двумя таблицами, которая реализована в виде пары «Внешний и первичный ключи» или же ключ «Уникальное поле». Связи создаются для того чтобы определить как столбцы одной таблицы связаны с другой таблицей. И связи используются для обеспечения ссылочной целостности и задания способа выборки данных из нескольких таблиц. Что касается обеспечения ссылочной целостности тут мы все понимаем а что касается выборки данных из нескольких таблиц – об этом мы поговорим на следующих уроках.

Между таблицами можно установить связь одной из трех типов: «Один ко многим», «Многие ко многим» и «Один к одному». Давайте рассмотрим каждую из них. Сперва мы рассмотрим связь «1 к 1». Эта связь говорит о том что одна запись таблицы А соответствует одной записи в таблице В и на оборот. Этот тип связи практически никогда не применяется. Единственный случай когда применение это типа связи оправдано это разбивка таблицы содержащей большое количество полей, то есть можно эту таблицу просто напросто с помощью такой связи разбить на несколько таблиц. Итак давайте рассмотрим наш пример. У нас есть таблички Customers и Orders. Между этими двумя табличками мы хотим построить связь «1 к 1». У таблички Orders в поле CustomerNo есть FK (внешний ключ). Табличка Customers имеет первичный ключ это поле CustomerNo. Если мы просто зададим Внешний ключ для Orders и первичный для Customers то мы построим связь «Один ко многим», но полю CustomerNo кроме ограничений внешнего ключа мы так же задали ограничение на уникальность. Тем самым мы построили связь «1 к 1». Следующий тип связи называется «Один ко многим». Этот тип связи является наиболее упротребляемым видом связи. В этом случае каждой записи таблицы А может соответствовать много записей в таблице В. В свою очередь одна запись в таблице В соответствует одной записи в таблице А. В таком случае таблица А будет наываться родительской а таблица В будет называться связной или дочерней.

Давайте рассмотрим наш пример: у нас есть две таблички Customers и Orders. В табличке Customers есть поле первичного ключа с именем CustomerNo. В табличке Orders есть поле внешнего ключа с таким же именем CustomerNo. Потому как мы для внешнего ключа Orders не указывали никаких других ограничений (допустим на уникальность) то тем самым мы создали связь «Один ко многим». В данном случае связь оправдана. Почему? Давайте рассмотрим суть этих таблиц. В табличке Customers у нас находиться информация о клиентах, в табличке Orders находится информация о заказах. И понятно что одному клиенту может соответствовать много заказов и каждому одному заказу может соответствовать только один клиент. То есть в данном случае такой тип связи будет оправдан. И так же мы рассмотрим связь «Многие ко многим». Этот вид связи говорит о том, что многие записи из таблици А могут соответствовать многим записям из таблицы В и наоборот. Такую связь в Vicrosoft SQL-Server можно организовать при помощи третей вспомогательной таблицы, в которой каждому первичному ключа из таблицы А сопоставлен первичный ключ из таблицы В. По сути связь «Многие ко многим » представляет собой несколько типов таких как «1 к 1» и «Многие к одному». При этом таблицы А и В расположены с одной стороны а вспомогательная таблица со стороны многих. Такой тип связи используется реже, но бывают такие ситуации когда без неё не обойтись. Давайте рассмотрим наш пример, который продемонстврирован в презентации. Итак, у нас есть две таблицы между которыми мы хотим построить связь «Многие ко многим». Эта связь между таблицой студентов и таблицей курсов. Вид связи между этими таблицами оправдан. Потому что один студен может быть записан одновременно на несколько курсов а также один курс может посещать одновременно несколько студентов. Вот тут как раз мы имеем связь «Многие ко многим» между таблицами «Стеденты» и «Курсы». Как мы уже говорили такой тип связи организуется с помощью третей таблицы, которая называется соединением. На примере нашей презентации это таблица под названием «StudentsCourses» . Первичный ключ этой таблицы состоит из ссылки на таблицу с курсами и ссылки на таблицу Students. Таким образом мы определяем связь «Многие ко многим» между курсами и студентами с помощью двух связей «Один ко многим». Первая такая связь организуется между таблицами StudentsCourses и Students а вторая между StudentsCourses и Courses. Первичный ключ таблицы StudentsCourses представляет собой сочитание первичного ключа таблицы Students и первичного ключа таблицы Courses. Давайте откроем последний пример Relations.sql. Сперва мы рассмотрим связь «1 к 1» или давайте рассмотрим связь «1 ко многим». Подключаемся к БД Shopdb а потом удалим таблички Orders и Customers если они у нас есть. Теперь давайте перейдем к 69-й строке и начнем связь «Один ко многим». Создаем табличку Customers на 69-й строке. В этой табличке будет 6 полей. Поле CustomerNo является первичным ключем для таблички Customers. Давайте создадим эту табличку. Теперь давайте создадим другую табличку Orders и давайте наладим связь между табличкой CustomerOrders «Один ко многим». 81-я строка мы создаем табличку Orders и указываем в этой табличке 4 поля OrderId, CustomerNo, OrderDate и Goods. OrderId это первичный ключ нашей таблички. CustomerNo это поле внешнего ключа. Это поле будет ссылаться на поле CustomerNo из ьаблички Customers. Создаем нашу табличку и тем же мы уже создали связь «1 ко многим». Потому как в таблице Orders возможно множество строк у которых одинаковое значение CustomerNo, тем самым множество заказов будет относится к одному и тому же клиенту. Теперь давайте вставим две строки в табличку Customers на 95-й и 96-й строке: это Петренко Петр Петрович и Иваненко Иван Иванович. И давайте создадим заказы для наших клиентов. Заполняем табличку Orders с 98-й по 104-ю строку. И выбираем все данные из таблиц Orders и Customers. Теперь давайте с помощью визуальных средств Management Studio посмотрим на структуру нашей БД. Для этого мне потребуется перейти ко вкладке Object Explorer, найти мою БД и добавить диаграмму БД. Я Нахожу каталог DataBases Diagrams, нажимаю New Diagram, нажимаю Yes и у меня появляется окошко, которое просит выбрать таблички которые я хочу добавить в конструктор диаграмм БД. Я добавляю две свои таблички. Я добавил таблички и теперь действительно могу убедиться что связь между таблицами «Многие к одному». Customers и Orders, мы видим ключ, который говорить о том что одному клиенту соответствует множество или бесконечность заказов и каждому заказу соответствует один клиент. Закрываем диаграмму БД. И посмотрим какие образом можно наладить связь «1 к 1». Это сделать очень просто. Для этого нужно будет немножко изменить связь «один ко многим». А Именно для поля с внешним ключом задать ограничение на уникальность. Давайте перейдем к 14-й строке нашего кода. Сперва удалим наши таблички, создадим заново табличку Orders и теперь для поля Customers мы кроме ограничения внешнего ключа установим еще ограничение на уникальность. То есть теперь в табличке Orders не будет записей, которые имеют одинаковое значение CustomerNo то есть один клиент у нас сможет заказать что то только один раз. Создаем Orders. Записываем данные в табличку Customers и Orders и давайте попробуем еще сделать так что бы наши клиенты заказали еще по одной единице продукции. У нас не получается. Теперь давайте построим диаграмму наших БД. Скорей всего она не будет работать но давайте попробуем. DataBase Diagrams Tables – создаем новую диаграмму, добавляю таблички и вот видно что связь между таблицами как 1 к 1, и теперь давайте так же попробуем создать связь «Многие ко многим». Такой вид связи мы реализуем на примере таблиц студентов и курсов. Сперва давайте удалим таблички Students, StudentsCourses, Courses если у нас такие таблички есть. Дальше, создаем заново таблички. Сперва давайте создадим таблицу Students, она имеет 5 полей. Первое поле : StudentId- это первичный ключ данной таблицы. Дальше есть поле Fname VarChar на 50 символов, LName, Email и Phone. Создаем таблицу. Дальше создаем таблицу курсов Courses, в ней есть три поля. Первое из них это CoursesId это ID курсов. Так же есть поле CoursesName и поле Price. Пока что между этими таблицами нет никакой связи, они никак не связаны между собой. Мы хотим создать связь многие ко многим, так что придется создавать промежуточную таблицу, которая реализовала эту связь. Эта таблица имеет имя StudentsCorses и она имеет ссылку на таблицу Students и одну ссылку на таблицу Courses. StudentsId это внешний ключ ссылающийся на поле Students id таблицы Students. И имя внешнего ключа, который ссылается на поле CoursesId таблицы Courses. Итак, наша только что созданная таблица будет иметь связь один ко многим с таблицой Students и один ко многим с таблицей Courses. Соответственно таблицы Students и Courses будут связи «многие ко многим». Так же следует не забывать добавлять первичный ключ для ссылающихся столбцов. То есть для нашей соеденяющей таблицы первичный ключ будет на поле StudentId и CourseId. Это нужно для того что бы не дать возможности нашим менеджерам записать двух одинаковых студентов на один и тот же курс.

Итак, создали все таблички и теперь можем добавлять в них данные. Сперва добавляем наших студентов: Петренка, Иваненка и Максима и дальше добавляем перечень курсов в табличку Courses. И сейсчас для того что бы связать данные с табличке Students Courses мы вставляем данные в табличку StudentsCourses. Пробуем вставить данные и дальше выбираем все данные из таблиц Students, StudentsCorses и Courses. Итак, в итоге что мы имеем. К примеру давайте посмотрим на какие курсы записан студент Петренко, у него айди (1). Идем к таблицам Students Courses и смотрим какие записи имеют значение (1) в поле айди. Только одна запись соответственно ходит только на один курс. Этот курс имеет айди (1). Он ходит на курс SQL ESSENTIAL. Давайте посмотрим на студента Иваненка. У этого студента айди (2), ищем соответствующие строки в таблице StudentsCourses и видим что студент ходит на 2 курса с айди (1 и 2). Соответственно ходит на курс SQL ESSENTIAL и на курс C# Proffesional. То есть одному студенту может соответствовать одновременно несколько курсов. Теперь давайте отдельно посмотрим на курсы, для начала на курс SQL ESSENTIAL. Курс SQL ESSENTIAL у нас имеет айди (1), давайте посмотрим какие записи соответствуют этому курсу в табличке StudentCourses. Смотрим на эту табличку, на поле CourseId. Таких записей аж 3. Соответственно можем определить что на курс SQL ESSENTIAL ходит 3 студента (Петренко, Иваненко и Максимов). Давайте также попробуем построить для этих таблиц диаграмму. Заходим в OdjectExplorer, выбираем интересующую нас БД Shopdb, нас интересует сейчас диаграмма, создаем новую диаграмму и в конструктор диаграмм помещаем 3 таблицы. Это таблица Students, StudentsCourses и таблица Courses. Соответственно увидим вот такую вот картинку. Видим что таблицы курсов и студентов у нас находятся на стороне 1 а таблицы StudetsCorses на второй стороне (на стороне «Многие»). Соответственно между Students и Corses существует связь «Многие ко многим». На сегодня это было все примеры. Спасибо за внимание. До свидания.

© 2017 ITVDN, все права защищены