11 SQL
11 SQL
Знакомимся с SQL
Замечание
Полную спецификацию стандарта SQL:2016 вы можете найти в интернете на сайте
ISO, например по адресу [Link]
Возможности SQL 197
Возможности SQL
Если читатель только начинает знакомиться с SQL, то необходимо сра-
зу заметить, что это весьма мощный, но далеко не всемогущий язык.
В сферу интересов SQL не попали задачи, стоящие перед прикладным и
тем более системным программистом. Ни реализации низкоуровневых
операций ввода-вывода, ни вопросы построения пользовательского ин-
терфейса, ни организации работы с периферийными устройствами и т.
п. Одним словом, на SQL не напишешь ни одного даже самого элемен-
тарного приложения для Windows, OS X, Linux или для любой другой ОС.
Предопределенные типы
Точные числовые типы (exact numeric) предназначены для обслужива-
ния целочисленных значений и значений, имеющих дробную часть без
потерь точности. При задании такого типа данных необходимо указать
два аргумента: точность (n) и масштаб (m). Точность задает общее число
значащих цифр, используемых при отображении числа. Масштаб опре-
200 Глава 11. Знакомимся с SQL
Спецификация Описание
NUMERIC [(n[,m])] Точное число, описываемое аргументами n и m
DECIMAL [(n[,m])] В отличие от NUMERIC, способно хранить число дальше с
или большей точностью, чем определено в аргументе m. Поэто-
DEC [(n[,m])] му говорят, что NUMERIC задает реальное значение точно-
сти, а DECIMAL – минимальное значение точности
BIGINT Тип данных, предназначен для хранения больших целых
чисел (обычно 64 бит). Типы данных BIGINT, INTEGER
и SMALLINT являются частным случаем типа данных
NUMERIC, у которого масштаб установлен в 0, а точность
определена возможностями СУБД
INTEGER
Тип данных, предназначен для хранения целых чисел
или
(обычно 32 бит)
INT
SMALLINT Тип данных, предназначен для хранения малых целых чи-
сел (обычно 16 бит)
Количество байт, необходимых для хранения значений NUMERIC и
DECIMAL, состоит в прямой зависимости от размерности аргумента n. На-
пример, если вы намерены хранить число из 15–16 сохраняемых зна-
ков, то вам потребуется 8 байт, 34–36 знаков – 16 байт.
Замечание
Практически во всех СУБД для работы с денежными величинами на базе NUMERIC
реализован свой собственный специализированный тип данных. Такие типы дан
ных хранят действительные числа с точностью до 4-го знака после запятой.
Спецификация Описание
REAL Точность и предел значений зависят от СУБД. Как прави-
ло, занимает в памяти 6 байт и в состоянии хранить число
в интервале от –3,4Е – 38 до +3,4Е + 38 с точностью до
7 цифр после запятой
FLOAT [(n)] Аргументом n определяется минимальное значение точ-
ности. Если значение n не указано, то потребует 8 байт
памяти. Тип данных способен хранить число в интервале
от 1,7Е – 308 до +1,7Е – 308 с точностью до 15 знаков
DOUBLE PRECISION Точность определяется версией СУБД, превышает точность
REAL
Спецификация Описание
CHARACTER [n], Тип данных предназначен для создания тек-
или сокращенно стовой строки фиксированной длины. Коли-
CHAR[n] чество символов в строке определяется в
квадратных скобках после указания типа
данных. Если в поле типа CHAR помещается
текстовое значение меньшего размера, чем
размерность поля, то оставшиеся позиции
символов заполнятся пробелами
CHARACTER VARYNG[n], Текстовая строка переменной длины. Мак-
или сокращенно симальный размер строки определяется в
VARCHAR[n] квадратных скобках. Преимущество такого
типа данных над типом CHAR заключается в
том, что здесь пустые позиции не заполня-
ются пробелами и, соответственно, таблица
требует меньшего размера оперативной и
дисковой памяти
NATIONAL CHARACTER [n], Строка национального символьного набора
или сокращенно фиксированной длины
NCHAR [n]
NATIONAL CHARACTER VARYING [n], Строка национального символьного набора
или сокращенно переменной длины
NCHAR VARYING [n]
CHARACTER LARGE OBJECT [n], Тип данных CHARACTER LARGE OBJECT пред-
или сокращенно назначен для определения столбцов таблиц,
CLOB [n] хранящих большие группы символов
NATIONAL CHARACTER LARGE Тип данных NATIONAL CHARACTER LARGE
OBJECT [n] OBJECT предназначен для определения
столбцов таблиц, хранящих большие группы
национальных символов
Типы данных SQL 203
Спецификация Описание
BIT [n] Битовая последовательность фиксированной
длины. Аргумент n устанавливает длину после-
довательности в битах. Если аргумент отсутствует
(или установлен в 1), то тип данных используется
для создания полей логического типа (Да/Нет).
Особенность типа данных фиксированной длины
в том, что попытка записать в поле этого типа зна-
чения меньшей длины, чем указано в аргументе n,
приведет к ошибке
BIT VARYNG [n] Битовая последовательность переменной длины.
Максимальное значение битовой последователь-
ности указывается в аргументе n
BINARY LARGE OBJECT [n], Тип данных предназначен для хранения больших
или сокращенно объектов. Например, файлов мультимедиа и изо-
BLOB [n] бражений
Спецификация Описание
DATE Тип данных включает три поля:
YEAR (год) – от 0001 до 9999;
MONTH (месяц) – от 01 до 12;
DAY (день) – от 01 до 31.
Формат записи: «yyyy–mm–dd».
Полное число позиций, требуемых для отображе-
ния даты (вместе с разделителями), – 11
TIME [(n)] Тип данных включает три поля:
HOUR (часы), MINUTE (минуты), SECOND (секун-
ды). Если аргумент точности (n) не определен, то
полное число позиций (вместе с разделителями)
равно 8, а формат записи: «hh:mm:ss». Если вы
укажете аргумент точности, то получите возмож-
ность работать с долями секунд
TIMESTAMP [(n)] Метка даты-времени, представляющая собой
комбинацию типов данных DATE и TIME
TIME WITH TIME ZONE Тип данных аналогичен TIME плюс два дополни-
тельных значения, характеризующих смещение
от Гринвичского меридиана в часах TIMEZONE_
HOUR и минутах TIMEZONE_MINUTE. Из-за учета
временной зоны количество позиций увеличива-
ется с 8 до 14
TIMESTAMP WITH TIME ZONE Метка даты-времени плюс смещение от Гринвича.
Число позиций для отображения даты, времени и
временной зоны максимальное – не менее 25
где: «start» и «end» – YEAR, MONTH, HOUR, MINUTE и SECOND. Явного опреде-
ления параметров «p» и «q» обычно не требуется, в этом случае в них
передается значение по умолчанию – 2. Двойка является минималь-
ным значением для «p», а верхняя ограничивающая планка зависит от
конкретной реализации СУБД. Например, мы планируем задать стол-
бец таблицы, предназначенный для хранения временного интервала до
10 000 лет, тогда в команде SQL появится следующая строка:
Непредопределенные типы
Большинство нестандартных, или, как их еще называют, непредо-
пределенных (non-predefined) типов данных вошло в состав SQL срав-
нительно недавно. В SQL:1999 появилась спецификация коллекции
(collection type) и массива (array), а в SQL:2003 к стандарту добавилось
мультимножество (multiset). Кроме того, стандарт признал право на су-
ществование таких типов, как последовательности, пользовательский
тип, тип данных XML, JSON и ссылочный тип (рис. 11.2).
Основная особенность непредопределенных типов в том, что даже в
действующем стандарте SQL их называют типами данных, не соответ-
ствующими SQL (non-predefined and non-SQL types). Несоответствий
много, но первое, что бросается в глаза, – нарушение требования к
атомарности данных, которое предписывает, чтобы в одной ячейке
таблицы хранилось одно-единственное неделимое значение. И дей-
ствительно, массив, мультимножество и последовательность тяжело
рассматривать как атомарный тип, и если такой тип данных опреде-
ляет колонку таблицы, то мы сразу сталкиваемся с проблемами нор-
мализации данных.
Указанное противоречие появилось из-за стремления разработчи-
ков стандарта расширить возможности реляционных БД по хране-
нию данных и в первую очередь разрешить хранить в БД сложные
объекты, дабы позволить разработчикам создавать объектно-реля-
ционные БД.
Массив
Синтаксическая конструкция по определению массива выглядит сле-
дующим образом:
тип_данных ARRAY [n];
Внимание!
Отсчет элементов в массиве SQL начинается с 1, а не с 0, как в большинстве языков
программирования!
Множество и мультимножество
Множество SET и мультимножество MULTISET отличаются друг от друга
лишь тем, что множество не допускает повтора значений, а мультимно-
жество допускает.
Для задания множества (мультимножества) следует указать тип под-
лежащих хранению данных:
тип_данных MULTISET
Последовательность
Последовательность строится средствами конструктора типа ROW и
представляет собой пары <имя_поля> <тип_данных>. В сконструирован-
ную последовательность может входить несколько пар. Для демонстра-
ции возможностей последовательностей воспользуемся следующим
примером: допустим, что в таблице DEMOTABLE мы собираемся хранить
фамилию, имя и отчество человека в одном столбце FIO. В таком случае
последовательность ROW позволит нам разделить столбец на три части
(листинг 11.1).
Пользовательский тип
Предопределенные типы данных далеко не всесильны и зачастую
не в состоянии охватить все потребности проектируемой БД. В подоб-
ных случаях стандарт предусматривает возможность проектирования
пользовательских типов данных (user-defined types), описание кото-
рых должно сохраняться в системном каталоге. При создании нового
типа данных следует опираться на уже существующие типы.
208 Глава 11. Знакомимся с SQL
Другие типы
Ссылочный тип (reference types, REF) может применяться при опре-
делении переменных и параметров. Значение ссылки REF может ука-
зывать на строку в типизированной таблице (таблице, описанной на
основе какого-то структурированного типа данных).
Язык XML (Extensible Markup Language) более подробно будет рас-
смотрен немного позднее (см. главу 19), поэтому мы пока ограничим-
ся лишь пояснением, что XML представляет собой язык наращиваемой
разметки, позволяющий описывать структурированные данные.
Тип JSON представляет собой текстовый формат обмена данными,
основанный на JavaScript.
Подводя итоги разговора о дополнительных типах данных SQL, сле-
дует отметить, что в рамках стандарта появились типы данных, проти-
воречащие ряду фундаментальных требований к реляционной модели.
Это указывает на стремление совершенствовать концепцию реляцион-
ных баз данных, внедряя в нее возможности объектно-ориентирован-
ного подхода (см. главу 22).
Замечание
Практически в каждой из СУБД имеются специфичные для нее типы данных, не
имеющие аналогов в стандарте. В качестве характерного примера стоит привести
PostgreSQL, в котором реализованы экзотические типы, предназначенные для хра
нения пространственных и геометрических данных (BOX, CIRCLE, LINE и т. д.).
Константы
Для числовых типов данных определены константы в виде последова-
тельности цифровых символов с необязательным заданием знака числа
и десятичной точкой:
- 1000.5
210 Глава 11. Знакомимся с SQL
Преобразование данных
Существование многочисленных типов данных подразумевает возмож-
ность взаимного преобразования значений из одного формата в дру-
гой. В большинстве СУБД поддерживается две разновидности преоб-
разования типов данных: неявное (implicit type conversions) и явное
(explicit type conversions). Неявное преобразование осуществляется
автоматически, без вмешательства разработчика. Например, в MySQL
вполне допустим подход, предложенный в листинге 11.4.
SELECT 2+'2';
-> 4
SELECT 'Hello'+2;
-> 2
Exact Numeric + + + + ? ? ? + ?
Approximate
+ + + + ? + ?
Numeric
Character + + + + + + + + + + ? + ?
212 Глава 11. Знакомимся с SQL
Date + + + + ? + ?
Time + + + + ? + ?
Timestamp + + + + + ? + ?
Year-Month
? + + + ? + ?
Interval
Day-Time Interval ? + + + ? + ?
Boolean + + + ? + ?
User Defined
? ? ? ? ? ? ? ? ? ? ? ? ? ?
Type
Binary Large
? + ?
Object
Reference type ? ? ? ? ? ? ? ? ? ? ? ? ? ?
Collection type ?
Row types ?
Операторы
В SQL, как, впрочем, и в любых других языках программирования, су-
ществует стандартный набор операторов, применяемых для осуществ
ления математических, логических операций, операций сравнения
и т. п.
Операторы 213
Операция присваивания
В SQL операция присваивания обычно осуществляется с помощью
оператора «=» (реже «:=»). Этот оператор широко применяется в теле
инструкции SELECT (листинг 11.7).
Арифметические операторы
Если речь идет о числовых типах данных, то с ними могут осуществ
ляться следующие стандартные арифметические операции:
«+» сложения;
«–» вычитания;
«*» умножения;
«/» деления.
Кроме того, в ряде диалектов SQL можно встретить операторы:
«DIV» целочисленного деления, например 7 DIV 2; -- результат 3;
«%» (MOD) остатка от деления, например 7 % 2; -- результат 1.
Еще раз подчеркнем, что, за небольшим исключением, в качестве
операндов должны выступать только числа. Технически, если вы допус
каете неявное приведение типов, то арифметические операции можно
осуществлять и со строковыми данными, при условии что они содер-
жат числовые значения. Кроме того, арифметические операторы могут
использоваться при работе с такими типами данных, как дата, время и
интервал (табл. 11.8).
Таблица 11.8. Операторы, применимые с датой, временем и интервалами
Логические операторы
Язык SQL поддерживает стандартный перечень логических опера-
ций:
AND – логическое умножение («И»);
OR – логическое сложение («ИЛИ»);
NOT – логическое отрицание («НЕ»).
Ряд диалектов поддерживает оператор:
XOR – исключение «ИЛИ».
В табл. 11.9 представлены результаты основных операций логическо-
го «И» и «ИЛИ».
Операторы сравнения
В результате выполнения операторы сравнения (отношения) возвра-
щают булевы значения TRUE или FALSE (табл. 11.10) .
Таблица 11.10. Операторы сравнения
Оператор Операция
< Меньше
> Больше
<= Меньше или равно
>= Больше или равно
= Проверка равенства
<=> Не равно, в том числе неопределенности NULL
!=, <> Проверка неравенства
Внимание!
Осуществляя операции сравнения, учитывайте, что среди сравниваемых значений
может оказаться неопределенность NULL.
Замечание
При желании в таблицу операторов сравнения можно добавить специфичные реля
ционные операторы IS NULL и IS NOT NULL, осуществляющие проверку равенства
и неравенства NULL.
Конкатенация строк
Операция конкатенации (соединения) строк обычно осуществляется
с помощью оператора «+», но, как всегда, существуют исключения. На-
пример, в диалектах SQL, применяемых в InterBase и FireBird, строки
соединяются оператором двойной вертикальной черты «||», например:
TXT='Hello, '||'InterBase!';.
Встроенные функции
Классический SQL вооружен сравнительно небольшим набором встро-
енных функций (табл. 11.11).
Таблица 11.11. Основные функции SQL
Функция Описание
BIT_LENGTH(битовая строка) Функция позволяет выяснить длину стро-
ки в битах
САSТ(значение AS тип данных) Функция преобразования исходного зна-
чения к новому типу данных. Допустимые
варианты конвертации типов данных
представлены в табл. 11.7
CHAR_LENGTH(символьная строка) Возвращает длину строки в символах
CURRENT_DATE Функция возвращает текущую дату
CURRENT_TIME(точность) Функция возвращает текущее время с
определенной точностью
CURRENT_TIMESTAMP(точность) Функция информирует о дате и времени с
указанной точностью
LOWER(строка) Преобразование текстовой строки к верх-
нему регистру
POSITION(подстрока IN строка) Позволяет выяснить позицию, с которой
начинается вхождение подстроки в строку
SUBSTRING(cтрокa FROM n FOR Возвращает часть строки, начиная с n-го
длина) символа с указанной длиной
Резюме 217
Функция Описание
TRANSLATE(строка USING функция) Преобразование строки с использовани-
ем указанной функции
TRIM(LEADING | TRAILING | BOTH Удаление из строки всех первых (LEADING),
символ FROM строка) последних (TRAILING) или первых и по-
следних (BOTH) символов. Например:
Резюме
Структурированный язык запросов SQL появился на свет вместе с ре-
ляционными базами данных в конце 70-х годов XX века. Это один из
немногих языков, которому за очень короткий промежуток времени
удалось добиться высокого статуса стандарта. На сегодняшний день
действующим стандартом языка реляционных баз данных является
SQL:2016, но, к сожалению, ни одна из имеющихся на рынке коммерчес
ких СУБД не в состоянии похвастаться абсолютным соответствием не
только SQL:2016, но и его предшественникам. Большинство компаний,
работающих на рынке программного обеспечения, уже давно идут сво-
им путем, развивая свои собственные диалекты SQL.
Неформально язык SQL можно разбить на несколько подъязыков:
подъязык определения данных, манипулирования данными, ограниче-
ния доступа к данным, управления курсором и управления транзакци-
ями.