Параметром называется переменная, используемая в SQL-операторе.
Применение параметров позволяет формировать SQL-операторы непосредственно во время выполнения приложения. Так, при использовании
Например:
INSERT INTO TBL1 (F_ID, F2, F3) VALUES (?, ?, ?)
Параметры могут быть именованными и позиционными.
Позиционные параметры указываются символом вопросительный знак (?), называемым маркером параметров. При выполнении оператора вместо параметра в соответствующую позицию SQL-оператора приставляется значение параметра.
Согласно спецификации языка SQL маркеры параметров нельзя размещать в следующих местах SQL-оператора:
SELECT ;BETWEEN (например, вместо SQL-оператораSELECT title_id, f_sales FROM tbl1 WHERE f_sales BETWEEN 4095 AND 12000нельзя записать
SELECT title_id, f_sales FROM tbl1 WHERE ? BETWEEN ? AND 12000 );
BETWEEN ;IN (например, вместо SQL-оператораSELECT f_ID, f_state FROM tbl1
WHERE f_state IN ('CA', 'CB')
нельзя записатьSELECT f_ID, f_state FROM tbl1 WHERE ? IN (?, ?) );
Выполняемый SQL-оператор может содержать несколько параметров.
Для использования параметра его первоначально следует определить (выполнить связывание параметра). Определение параметра заключается в указании типов для значения (С-тип) и для поля таблицы (SQL-тип), а также для указания буфера, в котором будет содержаться значение параметра, или номера параметра - для его последующего запроса во время выполнения. Определение параметра реализуется функцией SQLBindParameter (вместо функции SQLSetParam в ODBC 1.0).
Функция SQLBindParameter имеет следующее формальное описание:
SQLRETURN SQLBindParameter(
SQLHSTMT StatementHandle,
SQLUSMALLINT ParameterNumber,
SQLSMALLINT InputOutputType,
SQLSMALLINT ValueType,
SQLSMALLINT ParameterType,
SQLUINTEGER ColumnSize,
SQLSMALLINT DecimalDigits,
SQLPOINTER ParameterValuePtr,
SQLINTEGER BufferLength,
SQLINTEGER * StrLen_or_IndPtr);
Параметр StatementHandle ([Input]) указывает дескриптор оператора, параметр ParameterNumber ([Input]) задает номер параметра (по мере их вхождения в SQL-оператор), начиная с 1.
Параметр InputOutputType ([Input]) определяет тип параметра.
Параметр ValueType ([Input]) определяет тип значения переменной (С-тип), из которой будет извлекаться значение, передаваемое в базу данных, а параметр ParameterType ([Input]) указывает тип параметра (SQL-тип поля таблицы базы данных).
Параметр ColumnSize ([Input]) определяет размер столбца или указывает выражение, соответствующее маркеру параметра, а параметр DecimalDigits ([Input]) определяет количество десятичных знаков в столбце или указывает выражение, соответствующее маркеру параметра. Получить размер столбца и количество десятичных знаков в столбце можно при помощи функции ODBC API SQLDescribeCol.
Параметр ParameterValuePtr ([Deferred Input]) является указателем на буфер для данных, передаваемых в качестве параметра. Длина этого буфера определяется параметром BufferLength ([Input/Output]), а указатель на буфер для длины параметра задается параметром StrLen_or_IndPtr ([Deferred Input]).
Функция SQLBindParameter может возвращать следующие значения: SQL_SUCCESS, SQL_SUCCESS_WITH_INFO, SQL_ERROR, or SQL_INVALID_HANDLE.
Если перед выполнением функции SQLExecDirect значения параметров, используемых в запросе, не переданы на сервер, то функция возвращает код ответа SQL_NEED_DATA. Для передачи параметров в приложении могут использоваться функции SQLParamData и SQLPutData. Функция SQLParamData используется совместно с функцией SQLPutData для передачи значений параметров во время выполнения. Если функция SQLParamData возвращает значение SQL_NEED_DATA, то она также возвращает и номер параметра, для которого следует ввести значение. Передача значения параметра выполняется функцией SQLPutData.
Функция SQLParamData имеет следующее формальное описание:
SQLRETURN SQLParamData(
SQLHSTMT StatementHandle,
SQLPOINTER * ValuePtrPtr);
Параметр StatementHandle ([Input]) указывает дескриптор оператора, а параметр ValuePtrPtr ([Output]) указывает буфер, который был предназначен для хранения параметра функцией SQLBindParameter (указывается как значение параметра ParameterValuePtr ).
Функция SQLPutData позволяет приложению передавать данные параметра или столбца во время выполнения. При этом данные могут передаваться по частям.
Функция SQLPutData имеет следующее формальное описание:
SQLRETURN SQLPutData(
SQLHSTMT StatementHandle,
SQLPOINTER DataPtr,
SQLINTEGER StrLen_or_Ind);
Параметр StatementHandle ([Input]) указывает дескриптор оператора, параметр DataPtr ([Input]) определяет указатель буфера, в котором размещается значение параметра или столбец (значение соответствующего C-типа, указанного параметром ValueType функции SQLBindParameter или параметром TargetType функции SQLBindCol ), а параметр StrLen_or_Ind ([Input]) определяет длину передаваемых данных *DataPtr.
Следующий пример иллюстрирует применение функций OBDC API для передачи параметров, используемых оператором INSERT. Этот оператор содержит два параметра - для полей F1_ID и F2_PIC. Для каждого параметра приложение вызывает метод SQLBindParameter, определяющий С-тип данных и SQL-тип поля.
#define MAX_DATA_LEN 1024
SQLINTEGER cbF1_ID = 0, cbF2_PICParam, cbData;
SQLUINTEGER sF1_ID;
szPhotoFile;
SQLPOINTER pToken, InitValue;
SQLCHAR Data[MAX_DATA_LEN];
SQLRETURN retcode;
SQLHSTMT hstmt;
// Компиляция параметрического запроса
retcode = SQLPrepare(hstmt,
"INSERT INTO TBL1 (F1_ID, F2_PIC)
VALUES (?, ?)", SQL_NTS);
if (retcode == SQL_SUCCESS || retcode == SQL_SUCCESS_WITH_INFO) {
// Выполнение связывания параметров.
// Для 2 параметра передаем в ParameterValuePtr
// вместо адреса буфера номер параметра
SQLBindParameter(hstmt, 1, // Для 1 параметра
SQL_PARAM_INPUT,
SQL_C_ULONG,
SQL_INTEGER,
0, 0,
sF1_ID,
0,
cbF1_ID);
SQLBindParameter(hstmt, 2, // Для 2 параметра
SQL_PARAM_INPUT,
SQL_C_BINARY,
SQL_LONGVARBINARY,
0, 0,
(SQLPOINTER) 2, // Передаваемый номер
0,
cbF2_PICParam);
// Значения второго параметра будут передаваться
// во время выполнения.
// Длина параметра в макросе SQL_LEN_DATA_AT_EXEC
// равна 0. Это предполагает, что драйвер вернет
// значение "N" для типа SQL_NEED_LONG_DATA_LEN,
// указанного в функции SQLGetInfo.
cbF2_PICParam = SQL_LEN_DATA_AT_EXEC(0);
sF1_ID = MyGetNextID(); /* Запрос следующего значения поля F1_ID таблицы TBL1 */
retcode = SQLExecute(hstmt);
/* Для параметров времени выполнения (data-at-execution parameters) вызывается
функция SQLParamData для получения номера параметра, установленного функцией
SQLBindParameter. */
/* Вспомогательные функции MyInitData и MyGetData формируют значение параметра*/
/* Функция SQLParamData завершает процесс обработки параметра */
while (retcode == SQL_NEED_DATA) {
retcode = SQLParamData(hstmt, pToken); // Запрос
// значений параметров во время выполнения
if (retcode == SQL_NEED_DATA) {
MyInitData((SQLSMALLINT)pToken, InitValue);
while (MyGetData(InitValue,
(SQLSMALLINT)pToken, Data, cbData))
SQLPutData(hstmt, Data, cbData);
}
}
}
VOID MyInitData (sParam, InitValue)
SQLPOINTER InitValue;
{
SQLCHAR szPhotoFile[MAX_FILE_NAME_LEN];
/* Запрос у пользователя имени используемого BMP-файла, открытие этого файла и
возвращения дескриптора файла */
MyPromptPhotoFileName(szPhotoFile);
MyOpenBMPFile(szPhotoFile, (FILE *)InitValue);
break;
}
BOOL MyGetData (InitValue, sParam, Data, cbData)
SQLPOINTER InitValue;
SQLCHAR * Data;
SQLINTEGER * cbData;
BOOL Done;
{
/* Функция MyGetNextBMPData возвращает следующую часть данных и количество
передаваемых байтов (не более, чем MAX_DATA_LEN). */
Done = MyGetNextBMPData((FILE *)InitValue, Data,
MAX_DATA_LEN, cbData);
if (Done) { MyCloseBMPFile((FILE *)InitValue);
return (TRUE); }
return (FALSE);
}
Если значение атрибута дескриптора оператора SQL_ATTR_PARAMSET_SIZE больше 1 и SQL-оператор имеет хотя бы один маркер параметра, то функция SQLExecDirect будет выполняться последовательно для каждого значения параметра из массива, указанного параметром ParameterValuePointer функции SQLBindParameter.
Именованные параметры могут использоваться в том случае, когда в SQL-операторе выполняется вызов хранимой процедуры. Именованные параметры идентифицируются в соответствии с их именами, а не по порядку их расположения (как при позиционных параметрах). Именованные параметры, так же как и позиционные параметры, связываются с переменной посредством вызова функции ODBC API SQLBindParameter, но идентифицируются посредством поля SQL_DESC_NAME IPD-дескриптора (Implementation Parameter Descriptor). Именованные параметры также могут быть связаны с переменной при вызове функции SQLSetDescField или функции SQLSetDescRec.
Далее приведен пример применения именованных параметров, используемых при вызове предварительно
(CREATE PROCEDURE test @f_id int = 1, @f2 char(30) AS )
Первый параметр процедуры имеет значение, по умолчанию равное 1, а второй параметр @f2 обязательно должен быть указан при вызове процедуры. Параметр @f2 - это
// Компилирование вызова хранимой процедуры
SQLPrepare(hstmt, "{call test(?)}", SQL_NTS);
// Заполнение записи 1 для IPD-дескриптора
SQLBindParameter(hstmt, 1, SQL_PARAM_INPUT,
SQL_C_CHAR, SQL_CHAR,
30, 0, szF2, 0, cbValue);
// Получение IPD-дескриптора и определение полей
// SQL_DESC_NAMED и SQL_DESC_UNNAMED для записи #1.
SQLGetStmtAttr(hstmt, SQL_ATTR_IMP_PARAM_DESC,
hIpd, 0, 0);
SQLSetDescField(hIpd, 1, SQL_DESC_NAME,
"@f2", SQL_NTS);
SQLSetDescField(hIpd, 1, SQL_DESC_UNNAMED,
SQL_NAMED, 0);
// Если переменная szF2 была корректно
// инициализирована, то можно выполнять
// вызов хранимой процедуры
SQLExecute(hstmt);
Параметром называется переменная, используемая в SQL-операторе.
Применение параметров позволяет формировать SQL-операторы непосредственно во время выполнения приложения. Так, при использовании
Например:
INSERT INTO TBL1 (F_ID, F2, F3) VALUES (?, ?, ?)
Параметры могут быть именованными и позиционными.
Позиционные параметры указываются символом вопросительный знак (?), называемым маркером параметров. При выполнении оператора вместо параметра в соответствующую позицию SQL-оператора приставляется значение параметра.
Согласно спецификации языка SQL маркеры параметров нельзя размещать в следующих местах SQL-оператора:
SELECT ;BETWEEN (например, вместо SQL-оператораSELECT title_id, f_sales FROM tbl1 WHERE f_sales BETWEEN 4095 AND 12000нельзя записать
SELECT title_id, f_sales FROM tbl1 WHERE ? BETWEEN ? AND 12000 );
BETWEEN ;IN (например, вместо SQL-оператораSELECT f_ID, f_state FROM tbl1
WHERE f_state IN ('CA', 'CB')
нельзя записатьSELECT f_ID, f_state FROM tbl1 WHERE ? IN (?, ?) );
Выполняемый SQL-оператор может содержать несколько параметров.
Для использования параметра его первоначально следует определить (выполнить связывание параметра). Определение параметра заключается в указании типов для значения (С-тип) и для поля таблицы (SQL-тип), а также для указания буфера, в котором будет содержаться значение параметра, или номера параметра - для его последующего запроса во время выполнения. Определение параметра реализуется функцией SQLBindParameter (вместо функции SQLSetParam в ODBC 1.0).
Функция SQLBindParameter имеет следующее формальное описание:
SQLRETURN SQLBindParameter(
SQLHSTMT StatementHandle,
SQLUSMALLINT ParameterNumber,
SQLSMALLINT InputOutputType,
SQLSMALLINT ValueType,
SQLSMALLINT ParameterType,
SQLUINTEGER ColumnSize,
SQLSMALLINT DecimalDigits,
SQLPOINTER ParameterValuePtr,
SQLINTEGER BufferLength,
SQLINTEGER * StrLen_or_IndPtr);
Параметр StatementHandle ([Input]) указывает дескриптор оператора, параметр ParameterNumber ([Input]) задает номер параметра (по мере их вхождения в SQL-оператор), начиная с 1.
Параметр InputOutputType ([Input]) определяет тип параметра.
Параметр ValueType ([Input]) определяет тип значения переменной (С-тип), из которой будет извлекаться значение, передаваемое в базу данных, а параметр ParameterType ([Input]) указывает тип параметра (SQL-тип поля таблицы базы данных).
Параметр ColumnSize ([Input]) определяет размер столбца или указывает выражение, соответствующее маркеру параметра, а параметр DecimalDigits ([Input]) определяет количество десятичных знаков в столбце или указывает выражение, соответствующее маркеру параметра. Получить размер столбца и количество десятичных знаков в столбце можно при помощи функции ODBC API SQLDescribeCol.
Параметр ParameterValuePtr ([Deferred Input]) является указателем на буфер для данных, передаваемых в качестве параметра. Длина этого буфера определяется параметром BufferLength ([Input/Output]), а указатель на буфер для длины параметра задается параметром StrLen_or_IndPtr ([Deferred Input]).
Функция SQLBindParameter может возвращать следующие значения: SQL_SUCCESS, SQL_SUCCESS_WITH_INFO, SQL_ERROR, or SQL_INVALID_HANDLE.
Если перед выполнением функции SQLExecDirect значения параметров, используемых в запросе, не переданы на сервер, то функция возвращает код ответа SQL_NEED_DATA. Для передачи параметров в приложении могут использоваться функции SQLParamData и SQLPutData. Функция SQLParamData используется совместно с функцией SQLPutData для передачи значений параметров во время выполнения. Если функция SQLParamData возвращает значение SQL_NEED_DATA, то она также возвращает и номер параметра, для которого следует ввести значение. Передача значения параметра выполняется функцией SQLPutData.
Функция SQLParamData имеет следующее формальное описание:
SQLRETURN SQLParamData(
SQLHSTMT StatementHandle,
SQLPOINTER * ValuePtrPtr);
Параметр StatementHandle ([Input]) указывает дескриптор оператора, а параметр ValuePtrPtr ([Output]) указывает буфер, который был предназначен для хранения параметра функцией SQLBindParameter (указывается как значение параметра ParameterValuePtr ).
Функция SQLPutData позволяет приложению передавать данные параметра или столбца во время выполнения. При этом данные могут передаваться по частям.
Функция SQLPutData имеет следующее формальное описание:
SQLRETURN SQLPutData(
SQLHSTMT StatementHandle,
SQLPOINTER DataPtr,
SQLINTEGER StrLen_or_Ind);
Параметр StatementHandle ([Input]) указывает дескриптор оператора, параметр DataPtr ([Input]) определяет указатель буфера, в котором размещается значение параметра или столбец (значение соответствующего C-типа, указанного параметром ValueType функции SQLBindParameter или параметром TargetType функции SQLBindCol ), а параметр StrLen_or_Ind ([Input]) определяет длину передаваемых данных *DataPtr.
Следующий пример иллюстрирует применение функций OBDC API для передачи параметров, используемых оператором INSERT. Этот оператор содержит два параметра - для полей F1_ID и F2_PIC. Для каждого параметра приложение вызывает метод SQLBindParameter, определяющий С-тип данных и SQL-тип поля.
#define MAX_DATA_LEN 1024
SQLINTEGER cbF1_ID = 0, cbF2_PICParam, cbData;
SQLUINTEGER sF1_ID;
szPhotoFile;
SQLPOINTER pToken, InitValue;
SQLCHAR Data[MAX_DATA_LEN];
SQLRETURN retcode;
SQLHSTMT hstmt;
// Компиляция параметрического запроса
retcode = SQLPrepare(hstmt,
"INSERT INTO TBL1 (F1_ID, F2_PIC)
VALUES (?, ?)", SQL_NTS);
if (retcode == SQL_SUCCESS || retcode == SQL_SUCCESS_WITH_INFO) {
// Выполнение связывания параметров.
// Для 2 параметра передаем в ParameterValuePtr
// вместо адреса буфера номер параметра
SQLBindParameter(hstmt, 1, // Для 1 параметра
SQL_PARAM_INPUT,
SQL_C_ULONG,
SQL_INTEGER,
0, 0,
sF1_ID,
0,
cbF1_ID);
SQLBindParameter(hstmt, 2, // Для 2 параметра
SQL_PARAM_INPUT,
SQL_C_BINARY,
SQL_LONGVARBINARY,
0, 0,
(SQLPOINTER) 2, // Передаваемый номер
0,
cbF2_PICParam);
// Значения второго параметра будут передаваться
// во время выполнения.
// Длина параметра в макросе SQL_LEN_DATA_AT_EXEC
// равна 0. Это предполагает, что драйвер вернет
// значение "N" для типа SQL_NEED_LONG_DATA_LEN,
// указанного в функции SQLGetInfo.
cbF2_PICParam = SQL_LEN_DATA_AT_EXEC(0);
sF1_ID = MyGetNextID(); /* Запрос следующего значения поля F1_ID таблицы TBL1 */
retcode = SQLExecute(hstmt);
/* Для параметров времени выполнения (data-at-execution parameters) вызывается
функция SQLParamData для получения номера параметра, установленного функцией
SQLBindParameter. */
/* Вспомогательные функции MyInitData и MyGetData формируют значение параметра*/
/* Функция SQLParamData завершает процесс обработки параметра */
while (retcode == SQL_NEED_DATA) {
retcode = SQLParamData(hstmt, pToken); // Запрос
// значений параметров во время выполнения
if (retcode == SQL_NEED_DATA) {
MyInitData((SQLSMALLINT)pToken, InitValue);
while (MyGetData(InitValue,
(SQLSMALLINT)pToken, Data, cbData))
SQLPutData(hstmt, Data, cbData);
}
}
}
VOID MyInitData (sParam, InitValue)
SQLPOINTER InitValue;
{
SQLCHAR szPhotoFile[MAX_FILE_NAME_LEN];
/* Запрос у пользователя имени используемого BMP-файла, открытие этого файла и
возвращения дескриптора файла */
MyPromptPhotoFileName(szPhotoFile);
MyOpenBMPFile(szPhotoFile, (FILE *)InitValue);
break;
}
BOOL MyGetData (InitValue, sParam, Data, cbData)
SQLPOINTER InitValue;
SQLCHAR * Data;
SQLINTEGER * cbData;
BOOL Done;
{
/* Функция MyGetNextBMPData возвращает следующую часть данных и количество
передаваемых байтов (не более, чем MAX_DATA_LEN). */
Done = MyGetNextBMPData((FILE *)InitValue, Data,
MAX_DATA_LEN, cbData);
if (Done) { MyCloseBMPFile((FILE *)InitValue);
return (TRUE); }
return (FALSE);
}
Если значение атрибута дескриптора оператора SQL_ATTR_PARAMSET_SIZE больше 1 и SQL-оператор имеет хотя бы один маркер параметра, то функция SQLExecDirect будет выполняться последовательно для каждого значения параметра из массива, указанного параметром ParameterValuePointer функции SQLBindParameter.
Именованные параметры могут использоваться в том случае, когда в SQL-операторе выполняется вызов хранимой процедуры. Именованные параметры идентифицируются в соответствии с их именами, а не по порядку их расположения (как при позиционных параметрах). Именованные параметры, так же как и позиционные параметры, связываются с переменной посредством вызова функции ODBC API SQLBindParameter, но идентифицируются посредством поля SQL_DESC_NAME IPD-дескриптора (Implementation Parameter Descriptor). Именованные параметры также могут быть связаны с переменной при вызове функции SQLSetDescField или функции SQLSetDescRec.
Далее приведен пример применения именованных параметров, используемых при вызове предварительно
(CREATE PROCEDURE test @f_id int = 1, @f2 char(30) AS )
Первый параметр процедуры имеет значение, по умолчанию равное 1, а второй параметр @f2 обязательно должен быть указан при вызове процедуры. Параметр @f2 - это
// Компилирование вызова хранимой процедуры
SQLPrepare(hstmt, "{call test(?)}", SQL_NTS);
// Заполнение записи 1 для IPD-дескриптора
SQLBindParameter(hstmt, 1, SQL_PARAM_INPUT,
SQL_C_CHAR, SQL_CHAR,
30, 0, szF2, 0, cbValue);
// Получение IPD-дескриптора и определение полей
// SQL_DESC_NAMED и SQL_DESC_UNNAMED для записи #1.
SQLGetStmtAttr(hstmt, SQL_ATTR_IMP_PARAM_DESC,
hIpd, 0, 0);
SQLSetDescField(hIpd, 1, SQL_DESC_NAME,
"@f2", SQL_NTS);
SQLSetDescField(hIpd, 1, SQL_DESC_UNNAMED,
SQL_NAMED, 0);
// Если переменная szF2 была корректно
// инициализирована, то можно выполнять
// вызов хранимой процедуры
SQLExecute(hstmt);
Для получения официальных документов о завершении программы дополнительного профессионального образования (удостоверения о повышении квалификации, дипломов о профессиональной переподготовке и MBA) необходимо предоставить:
Внимание! Вы можете не заказывать доставку бумажной версии официального документы, а скачать его в электронном виде и распечатать самостоятельно. Информация о выданном документе в течение 1 месяца загружается в Федеральную информационную систему «Федеральный реестр сведений о документах об образовании и (или) о квалификации, документах об обучении» - ФИС ФРДО.
Доступ на новый сайт осуществляется с использованием адреса электронной почты, который был указан вами при регистрации на "старом". Мы постарались перенести все ваши данные с прежнего ресурса, однако не исключена вероятность потери части информации.
При возникновении проблемы со входом, воспользуйтесь функцией сброса пароля
Если вы обнаружите несоответствия, пожалуйста, сообщите нам.