Track
T‑SQL (Transact‑SQL) — это расширение стандартного SQL от Microsoft, разработанное специально для Microsoft SQL Server. Наряду со всеми базовыми возможностями SQL для запросов и управления данными T‑SQL добавляет функции процедурного программирования, которые позволяют писать более мощную и динамичную логику базы данных.
В этом руководстве я покажу, как работает T‑SQL и как эффективно применять его в реальных сценариях. Я также разберу типичные случаи использования — от выполнения запросов и написания хранимых процедур до автоматизации рутинных процессов — с практическими примерами.
Если вы новичок в SQL, начните с нашего курса Introduction to SQL или курса Intermediate SQL, если уже имеете некоторый опыт. Также рекомендую скачать и держать под рукой шпаргалку SQL Basics Cheat Sheet — в ней собраны наиболее распространённые функции SQL.
Что такое T-SQL и чем он отличается от SQL
Чтобы лучше понять T‑SQL, представьте SQL как универсальный язык, а T‑SQL — как специализированный профессиональный диалект.
SQL (Structured Query Language) — стандартный язык для работы с реляционными базами данных. Он декларативный: вы указываете, какой результат хотите получить (например, отбор или фильтрацию данных), а движок базы данных решает, как выполнить запрос.
T‑SQL, в свою очередь, — это расширение SQL от Microsoft, используемое в Microsoft SQL Server. Оно дополняет стандартный SQL возможностями процедурного программирования, позволяя пошагово управлять выполнением операций.
Из этого определения следует, что T‑SQL вводит ряд мощных возможностей, выходящих за рамки базовых запросов, включая:
-
Переменные: можно использовать ключевые слова
DECLAREиSET, чтобы сохранять данные в памяти и переиспользовать их в скриптах -
Управление потоком: можно использовать логику
IF,WHILEиBEGIN...ENDдля контроля выполнения и выбора нужного кода. -
Обработка ошибок: T‑SQL вводит блоки
TRY...CATCH, которые позволяют перехватывать ошибки и обрабатывать их без падения всей операции. -
Хранимые процедуры: можно создавать многократно используемые блоки логики, выполняющиеся внутри базы данных.
Если вы работаете с SQL Server, у DataCamp есть множество полезных материалов. Для начала рекомендую пройти курс Introduction to SQL Server, чтобы освоить основы SQL Server для анализа данных.
Базовый синтаксис и структура T-SQL
T‑SQL использует тот же базовый синтаксис, что и стандартный SQL, поэтому, если вы уже знакомы с SQL, разобраться будет несложно. В этом разделе я приведу самые распространённые инструкции T‑SQL с простыми практическими примерами.
SELECT, INSERT, UPDATE, DELETE
Эти команды стандартны для большинства диалектов SQL, включая Microsoft SQL Server, для которого создан T‑SQL.
SELECT
Команда для извлечения данных из конкретных таблиц. Например, запрос ниже получает FirstName и LastName из таблицы Customers.
-- Retrieve data from the Customers table
SELECT FirstName, LastName
FROM Customers
WHERE Country = ‘USA’; -- Filters rows to only customers in the USA
INSERT
Эта команда используется для вставки новых данных в таблицу. Запрос ниже вставляет новую строку в таблицу customers.
-- Insert a new row into a table
INSERT INTO customers (FirstName, city)
VALUES (‘Alice’, ‘Nairobi’);
UPDATE
Команда для изменения существующих данных в базе. Например, запрос ниже меняет название города на «Mombasa» для пользователя «Alice».
-- Update existing data
UPDATE customers
SET city = ‘Mombasa’
WHERE FirstName= ‘Alice’; -- Always use WHERE to avoid updating all rows
DELETE
Команда удаляет данные из базы. Например, запрос ниже удаляет строку, где FirstName равно «Alice».
-- Delete data from a table
DELETE FROM customers
WHERE FirstName= ‘Alice’; -- Filters which rows to remove
Рекомендую пройти наш трек навыков SQL Server Fundamentals, чтобы узнать больше о суммировании и анализе данных с помощью функций SQL Server
Пакетное выполнение
Одна из особенностей T‑SQL — выполнение кода пакетами. Пакет — это группа из одного или нескольких операторов SQL, отправляемых в SQL Server как единое целое.
Ключевое слово GO используется для разделения пакетов:
-- First batch
SELECT * FROM Customers;
GO
-- Second batch (executed separately)
SELECT * FROM Orders;
GO
Важно отметить, что:
-
GO— не команда T‑SQL, но она распознаётся инструментами вроде SQL Server Management Studio. -
Она обозначает конец одного пакета и начало другого.
-
Переменные не сохраняются между пакетами. Временные объекты, напротив, сохраняются между пакетами в пределах одной сессии.
Комментарии и форматирование
В T‑SQL можно использовать комментарии, чтобы сделать код SQL более читаемым и удобным в сопровождении. Доступны однострочные и многострочные комментарии, как показано ниже:
-- This query retrieves all customers
SELECT * FROM Customers;
/* This query retrieves customers
from the USA and Canada */
SELECT *
FROM Customers
WHERE Country IN ('USA', 'Canada');
Переменные и типы данных в T-SQL
T‑SQL позволяет сохранять значения в переменных и использовать их в запросах, делая ваши скрипты более гибкими и динамичными. Рассмотрим, как создавать такие переменные.
Объявление переменных
Для создания переменной используется ключевое слово DECLARE. По соглашению все имена переменных T‑SQL должны начинаться с символа @.
-- Declares a variable to store text
DECLARE @CustomerName VARCHAR(50);
Присвоение значений
Значения можно присваивать с помощью SET (рекомендуется для одиночных значений) или SELECT (удобно при получении из таблицы).
-- Assign using SET
SET @CustomerName = 'Alice';
-- Assign using SELECT
SELECT @Age = 30;
Например, запрос ниже возвращает список клиентов, живущих в Лондоне, используя переменную вместо жёстко заданного значения.
-- Assign the variable city
DECLARE @City VARCHAR(50);
SET @City = 'London';
-- Use the variable in a query
SELECT name, city
FROM customers
WHERE city = @City; -- Filters results based on variable value
Распространённые типы данных
Ниже приведены некоторые распространённые типы данных T‑SQL, которые стандартны для типов данных SQL:
-
INT: целые числа, например 1, 100. -
VARCHAR(n): текст переменной длины — имена, электронная почта и т. п. -
DATETIME: значения даты и времени -
DECIMAL(p, s): числа фиксированной точности, например суммы денег.
Управление потоком в T-SQL (IF, WHILE, BEGIN...END)
Одно из преимуществ T‑SQL — возможность добавлять программную логику в запросы. Вместо простого извлечения данных вы можете управлять тем, как и когда выполняется код. Ниже приведены примеры управляющих конструкций.
IF...ELSE (условное выполнение)
Оператор IF позволяет выполнять блок кода только при выполнении определённого условия. Если условие ложно, можно использовать ELSE для альтернативного действия.
Например, запрос ниже подсчитывает общее число заказов, затем выводит «High order volume», если их больше 100, или «Low order volume», если меньше 100.
DECLARE @TotalOrders INT;
SELECT @TotalOrders = COUNT(*)
FROM Orders; -- Count total number of orders
IF @TotalOrders > 100
BEGIN
PRINT 'High order volume'; -- Runs if condition is true
END
ELSE
BEGIN
PRINT 'Low order volume'; -- Runs if condition is false
END
Циклы WHILE (итерационная логика)
Цикл WHILE повторяет блок кода, пока условие истинно. Полезно для задач, выполняемых «порциями», или для генерации тестовых данных.
Запрос ниже инициализирует счётчик значением 1 и в цикле выводит текущее число, увеличивая его на 1, пока не достигнет 5.
DECLARE @Counter INT = 1;
WHILE @Counter <= 5
BEGIN
PRINT @Counter; -- Prints numbers from 1 to 5
SET @Counter = @Counter + 1; -- Increment counter
END
BEGIN...END (группировка операторов)
Конструкция BEGIN...END используется для группировки нескольких операторов в единый блок, чтобы весь сгруппированный код выполнялся атомарно.
Например, запрос ниже выведет и «Customers found in USA», и «Proceeding with operation». Без BEGIN...END был бы выполнен только первый оператор после IF.
IF EXISTS (SELECT 1 FROM Customers WHERE Country = 'USA')
BEGIN
PRINT 'Customers found in USA';
PRINT 'Proceeding with operation'; -- Both statements run together
END
Когда полезно управление потоком?
Управляющие конструкции в T‑SQL обычно используют для:
- Автоматизации: выполнение расписных скриптов или задач обслуживания
- Проверки данных: проверка условий перед вставкой или обновлением
- Пакетной обработки: обработка данных шагами или в циклах
- Бизнес‑логики: применение правил непосредственно в базе данных
Хранимые процедуры в T-SQL
Хранимая процедура — это сохранённая коллекция операторов T‑SQL, которую можно многократно переиспользовать. Вместо того чтобы каждый раз отправлять на сервер большой блок кода из приложения, вы сохраняете код на сервере и вызываете его по имени.
Хранимые процедуры удобны, потому что их можно использовать много раз. Предкомпилированные планы выполнения повышают эффективность и скрывают сложную логику за простым интерфейсом.
Например, эта хранимая процедура получает имя и фамилию клиента по указанному идентификатору.
-- Create a stored procedure named GetCustomerByID
CREATE PROCEDURE GetCustomerByID
@CustomerID INT -- Input parameter to pass a customer ID
AS
BEGIN
-- Select the first and last name of a customer
SELECT FirstName, LastName
FROM Customers
WHERE CustomerID = @CustomerID; -- Filter to match the given ID
END;
Затем можно выполнить хранимую процедуру следующим запросом:
-- Calls the procedure
EXEC GetCustomerByID @CustomerID = 1; Функции в T-SQL
T‑SQL включает как встроенные функции, так и определяемые пользователем функции (UDF), используемые для преобразования данных.
Встроенные функции
Эти функции уже доступны в SQL Server и могут использоваться непосредственно в запросах.
Строковая функция
Функция, преобразующая строковые типы данных. Например, запрос ниже выбирает имена из таблицы Customers и превращает их в верхний регистр.
-- Converts text to uppercase
SELECT UPPER(FirstName)
FROM Customers;
Функция даты
Эта функция работает с датами. Запрос ниже возвращает текущие системные дату и время.
-- Returns current date and time
SELECT GETDATE();
Агрегатная функция
Функции для агрегирования значений в таблице. Например, запрос ниже подсчитывает общее число строк (клиентов) в таблице Customers.
-- Counts rows
SELECT COUNT(*) AS TotalCustomers
FROM Customers;
Определяемые пользователем функции (UDF)
Вы также можете создавать собственные функции и переиспользовать логику в нескольких запросах.
Скалярная функция
Скалярная функция возвращает одно значение и полезна, когда нужен единичный вычисленный результат, например форматирование или вычисления. В запросе ниже функция принимает имя и фамилию как входные параметры и возвращает их в виде полного имени.
-- Create a function that combines the first and last name
CREATE FUNCTION GetFullName
(@FirstName VARCHAR(50), @LastName VARCHAR(50))
RETURNS VARCHAR(100)
AS
BEGIN
RETURN @FirstName + ' ' + @LastName; -- Concatenates the two values
END;
Табличные функции
Табличные функции возвращают таблицу. Например, функция ниже возвращает таблицу всех клиентов из указанной страны.
-- Create a table-valued function named GetCustomersByCountry
CREATE FUNCTION GetCustomersByCountry (@Country VARCHAR(50))
RETURNS TABLE -- Specifies that the function returns a table
AS
RETURN
(
-- Select all columns from the Customers table
SELECT *
FROM Customers
WHERE Country = @Country -- Filter rows by the given country
);
Рекомендую пройти полный карьерный трек SQL Server Developer, который не только научит создавать, обновлять и выполнять хранимые процедуры, но и поможет освоить агрегатные функции, объединение, вставку и удаление таблиц и многое другое.
Обработка ошибок в T-SQL
T‑SQL использует блоки TRY...CATCH для обработки ошибок без остановки всего скрипта. Это важно, поскольку предотвращает неожиданные сбои и позволяет возвращать понятные сообщения для отладки или логирования.
Например, запрос ниже пытается выполнить вычисление, вызывающее ошибку, перехватывает её и выводит читаемое сообщение вместо аварийного завершения.
BEGIN TRY
-- Attempt to run this code
SELECT 1 / 0; -- This causes a divide-by-zero error
END TRY
BEGIN CATCH
-- Runs if an error occurs in the TRY block
PRINT 'An error occurred: ' + ERROR_MESSAGE(); -- Displays the error message
END CATCH;
Транзакции в T-SQL
Транзакция гарантирует, что группа операций либо выполнится вся, либо не выполнится вовсе. Это соответствует принципам ACID, которые обеспечивают согласованность базы данных даже при сбоях, например отключении питания посреди обновления.
В примере ниже транзакция переводит деньги с одного счёта на другой и сохраняет оба изменения вместе.
BEGIN TRANSACTION; -- Start the transaction
-- Deduct money from Account 1
UPDATE Accounts
SET Balance = Balance - 100
WHERE AccountID = 1;
-- Add money to Account 2
UPDATE Accounts
SET Balance = Balance + 100
WHERE AccountID = 2;
COMMIT; -- Save all changes permanently
Если что-то пошло не так, вы можете использовать функцию ROLLBACK, чтобы отменить транзакцию и вернуть данные в прежнее состояние.
-- Undo all changes made in the current transaction
ROLLBACK;
Транзакции в T‑SQL важны, поскольку обеспечивают целостность данных, особенно в критичных системах, например финансовых приложениях, где частичные обновления могут привести к несогласованности.
Вы можете пройти наш карьерный трек Transactions and Error Handling in SQL Server, который охватывает транзакции и обработку ошибок в SQL Server.
Распространённые возможности T-SQL для анализа данных
В T‑SQL есть инструменты, особенно полезные для специалистов по данным. Рассмотрим примеры и то, как применять их в анализе данных.
Оконные функции
Оконные функции выполняют вычисления по строкам без объединения их в один результат. Чаще всего применяются для ранжирования, накопительных итогов и продвинутой аналитики.
В примере ниже запрос присваивает каждой записи клиента уникальный номер строки на основе CustomerID.
-- Assigns row numbers to customers
SELECT
FirstName,
ROW_NUMBER() OVER (ORDER BY CustomerID) AS RowNum -- Assigns row numbers
FROM Customers;
В запросе:
-
ROW_NUMBER(): присваивает уникальные номера строк
-
RANK(): присваивает рейтинг с пропусками при равенствах -
OVER(): определяет окно (упорядочивание/разбиение)
Рекомендую ознакомиться с нашей шпаргалкой по оконным функциям SQL, которую можно скачать: это удобный справочник по различным видам оконных функций в SQL. Также посмотрите наш курс Intermediate SQL Server, чтобы узнать больше об использовании T‑SQL в анализе данных, включая оконные функции для суммирования.
Общие табличные выражения (CTE)
CTE (Common Table Expressions) создают временный набор результатов, который можно переиспользовать в рамках запроса. Запрос ниже формирует временный список клиентов из США, а затем извлекает из него данные.
-- Define a CTE
WITH CustomerCTE AS (
SELECT FirstName, Country
FROM Customers
WHERE Country = 'USA' -- Filter only USA customers
)
-- Query the CTE
SELECT *
FROM CustomerCTE;
Рекурсивные CTE, в свою очередь, — это особый тип CTE, который ссылается на себя в определении, позволяя выполнять повторяющиеся операции. Они идеально подходят для работы с иерархическими данными, например организационными структурами.
Рекомендую пройти курс Hierarchical and Recursive Queries in SQL Server, чтобы научиться писать продвинутые запросы в SQL Server, включая CTE и рекурсивные CTE, на практических примерах.
Временные таблицы
Временные таблицы хранят данные для краткосрочного использования в рамках сессии. Они полезны для промежуточной загрузки данных, упрощения многошаговых преобразований или повышения производительности сложных запросов.
Чтобы продемонстрировать работу временных таблиц в T‑SQL, рассмотрим три блока запросов. В первом создаётся временная таблица, затем в неё загружаются данные о клиентах, после чего выполняется выборка в пределах той же сессии.
-- Create a temporary table
CREATE TABLE #TempCustomers (
FirstName VARCHAR(50),
Country VARCHAR(50)
);
-- Insert data into the temporary table
INSERT INTO #TempCustomers
SELECT FirstName, Country
FROM Customers;
-- Retrieve data from the temporary table
SELECT * FROM #TempCustomers;
Важно: имена временных таблиц начинаются с #, и они автоматически удаляются при завершении сессии.
T-SQL и другие диалекты SQL
Все диалекты SQL имеют общую основу, но каждая СУБД добавляет собственный синтаксис и возможности. T‑SQL разработан специально для Microsoft SQL Server, что влияет на его работу и области наилучшего применения.
T-SQL и PostgreSQL (PL/pgSQL)
PostgreSQL использует PL/pgSQL для процедурной логики — схожий с T‑SQL подход, но с иным синтаксисом и сильными сторонами. Ниже таблица с кратким сравнением:
|
Категория |
T-SQL (SQL Server) |
PostgreSQL (PL/pgSQL) |
|
Процедурный язык |
Встроен в T‑SQL |
Использует PL/pgSQL |
|
Синтаксис переменных |
|
|
|
Именование переменных |
Префикс |
Без префикса (например, |
|
Структура блока |
Проще: часто неявно или |
Явно: требуются |
|
Пример блока |
Стандартный пакет T‑SQL |
Заключён в |
|
Продвинутые типы данных |
Ограничены |
Расширенная нативная поддержка (JSONB, массивы, геометрия) |
|
Инструменты и интеграция |
Тесная интеграция с инструментами SQL Server |
Гибкость на разных платформах |
|
Экосистема |
Оптимизирован для Windows, Azure, SSMS и Power BI |
Открытый исходный код, кроссплатформенность |
Ознакомьтесь с нашим треком навыков SQL for Database Administrators, чтобы научиться проектировать реляционные базы и оптимизировать запросы для повышения производительности.
T-SQL и MySQL
MySQL также поддерживает процедурный SQL, но в более простом и ограниченном варианте. Таблица ниже сравнивает синтаксис и возможности этих двух диалектов.
|
Категория |
T-SQL (Microsoft) |
MySQL |
|
Ограничение строк |
|
|
|
Обработка ошибок |
Надёжные блоки |
Более ограниченный синтаксис DECLARE HANDLER |
|
Процедурная логика |
Богатая, структурированная и хорошо программируемая |
Более простые и ограниченные процедурные возможности |
|
Аналитика |
Оконные функции и CTE |
Базовые аналитические возможности (улучшаются в новых версиях) |
|
Экосистема |
Связан с SQL Server и корпоративными инструментами |
Лёгковесный; ядро стека LAMP (Linux, Apache и т. д.) |
|
Лучше всего подходит для |
Сложной бизнес‑логики и хранилищ данных |
Веб‑приложений и высокоскоростных операций чтения |
Практические сценарии использования T-SQL
T‑SQL широко применяется не только для простых выборок. Ниже примеры, где он был для меня особенно полезен как для специалиста по данным.
Запросы для отчётности
T‑SQL часто используют для формирования отчётов напрямую из базы. Например, можно агрегировать продажи по регионам или ранжировать наиболее успешные товары с помощью оконных функций.
ETL‑процессы (Extract, Transform, Load)
Инженеры данных используют T‑SQL в конвейерах данных для подготовки и перемещения данных. Например, можно извлечь данные из промежуточных таблиц, преобразовать форматы, очистить несоответствия и загрузить их в итоговые отчётные таблицы.
Скрипты очистки данных
Если в вашей базе миллионы строк с разнородными форматами адресов, можно написать скрипт T‑SQL с циклами WHILE или CTE для поиска дублей, заполнения пропусков или стандартизации форматов.
Бэкенд‑логика в приложениях
Многие приложения полагаются на T‑SQL для реализации бизнес‑логики внутри базы данных. Можно использовать хранимые процедуры для операций CRUD, выполнять проверки перед вставкой данных или обрабатывать транзакции для критичных операций.
Типичные ошибки и лучшие практики
Хотя T‑SQL полезен для продвинутых запросов к базам, вы можете столкнуться с распространёнными проблемами. Ниже — типичные ошибки, с которыми я встречался при использовании T‑SQL:
-
Чрезмерное использование циклов вместо наборной логики: операции построчно при помощи
WHILEмогут замедлить производительность. SQL рассчитан на работу с наборами данных сразу. -
Недооценка индексов: неправильное использование индексов может сделать запросы медленными, особенно на больших таблицах.
-
Неправильное использование транзакций: выполнение нескольких связанных операций без обёртки в транзакцию может оставить данные в несогласованном состоянии при сбое посередине.
-
Игнорирование обработки ошибок: отсутствие блоков
TRY...CATCHусложняет отладку и может привести к тихим сбоям или непредсказуемой работе скриптов в продакшене.
Ниже — лучшие практики, которые я рекомендую для написания более эффективных и надёжных запросов:
-
Предпочитайте наборные запросы: используйте
JOIN,GROUP BYи оконные функции вместо циклов, когда это возможно. Это соответствует тому, как SQL Server оптимально обрабатывает данные. -
Пишите читаемый и поддерживаемый код: используйте понятные соглашения об именовании, единый стиль форматирования и добавляйте комментарии при необходимости. Так код будет понятнее, его проще отлаживать и в нём легче сотрудничать.
-
Тестируйте процедуры: всегда проверяйте хранимые процедуры и запросы с разными входными данными, чтобы убедиться в корректной работе и обработке крайних случаев.
Заключение
T‑SQL расширяет стандартный SQL за счёт программных возможностей, делая его гибким и мощным инструментом для автоматизации, обработки и анализа данных. Благодаря таким функциям, как переменные, хранимые процедуры и обработка ошибок, вы можете строить более динамичные и эффективные решения на базе данных.
В качестве следующего шага рекомендую пройти карьерный трек Associate Data Analyst по SQL, чтобы стать уверенным аналитиком данных. Наш курс Reporting in SQL также поможет вам овладеть построением сложных отчётов. И, наконец, получите нашу SQL Associate Certification, чтобы подтвердить мастерство в применении SQL для решения бизнес‑задач и выгодно выделиться среди профессионалов.
T-SQL: ответы на частые вопросы
Чем T-SQL отличается от стандартного SQL?
SQL в основном декларативен, тогда как T‑SQL сочетает декларативные запросы с процедурным программированием, позволяя управлять тем, как именно выполняются операции.
Нужно ли изучать SQL перед T-SQL?
Да, базовое понимание SQL важно, поскольку T‑SQL напрямую опирается на ключевые концепции SQL, такие как SELECT, INSERT, UPDATE и DELETE.
Доступен ли T-SQL во всех диалектах SQL?
Нет, T‑SQL специфичен для экосистемы Microsoft и используется преимущественно с Microsoft SQL Server и связанными инструментами, такими как Azure SQL.
Что такое хранимые процедуры и зачем они нужны?
Хранимые процедуры — это многократно используемые блоки кода T‑SQL, выполняемые внутри базы данных. Они помогают повысить производительность, обеспечить согласованность и упростить логику приложений.
Для чего используются оконные функции в T-SQL?
Оконные функции используются для продвинутых аналитических задач — ранжирования, накопительных итогов и сравнения значений между строками без группировки данных.