Как только закончена выборка информации о результирующем множестве, можно приступать к выборке собственно результирующего множества. В ODBC существует две функции базового уровня для выборки результатов: SQLBindCol() и SQLFetch(). Функция SQLBindCol() определяет область хранения данных результирующего множества, а SQLFetch() осуществляет выборку данных в области хранения. Алгоритм программы, использующей эти функции для возвращения данных из всех строк результирующего множества, предполагает выполнение следующих шагов:
1. Вызов SQLBindCol() один раз для каждого столбца, который должен быть возвращен из результирующего множества,
2. Вызов SQLFetch() для перемещения курсора на следующую строку и возврата данных из связанных столбцов,
3. Повторение шага 2 до тех пор пока SQLFetch() не возвратит SQL_NO_DATA_FOUND. Это указывает на то, что был достигнут конец результирующего множества. Если результирующее множество является пустым, то SQL_NO_DATA_FOUND будет возвращен сразу же при первом вызове SQLFetch().
Функция SQLFetch() извлекает строку данных из результирующего множества для выполненного SQL – оператора. Драйвер возвращает данные для всех столбцов, которые были связаны для предварительного хранения данных с помощью функции SQLBindCol(). Синтаксис функции SQLFetch():
RETCODE SQLFetch (hstmt)
Здесь hstmt – идентификатор выполненного оператора.
Если необходимо определить область хранения данных результирующего множества, которые должны быть извлечены, то вызывается функция SQLBindCol(). Каждый столбец, который требуется выбрать, связывается с помощью отдельного вызова функции.
Функция SQLBindCol() назначает область хранения в памяти и тип данных для столбца результирующего множества. Она определяет:
● Буфер хранения для получения содержимого столбца данных в результирующем множестве,
● Длину указанного буфера хранения,
● Область памяти для хранения длины столбца выборки
● Преобразование типа данных.
Синтаксис данной функции имеет следующий вид:
RETCODE SQLBindCol (hstmt, icol, fcType, rgbValue, cbValueMax,
pcbValue)
Таблица 19 Параметры функции SQLBindCol()
Тип | Аргумент | Использование | Описание |
HSTMT | hstmt | Вход | Идентификатор оператора |
UWORD | icol | Вход | Номер столбца результирующего множества, упорядоченный слева направо, начиная с 1 |
SWORD | fcType | Вход | С – тип данных столбца результирующего множества. Некоторые из возможных значений: SQL_C_BINARY, SQL_C_BIT, SQL_C_CHAR, SQL_C_DEFAULT, SQL_C_FLOAT, SQL_C_SLONG, SQL_C_SSHORT, SQL_C_ULONG, SQL_C_USHORT. SQL_C_DEFAULT определяет, что данные должны быть переданы в С – тип по умолчанию. |
PTR | rgbValue | Вход | Указатель области хранения данных. Если является нулевым указателем, то драйвер “отвязывает” столбец. Для “отвязывания” всех столбцов программа вызывает SQLFreeStmt() с опцией SQL_UNBIND. |
Продолжение таблицы 19
SDWORD | cbValueMax | Вход | Максимальная длина буфера rgbValue. Для символьных данных буфер должен предусматривать место для нуль – окончания строки. |
SDWORD* | pcbValue | Вход | SQL_NULL_DATA или размер возвращаемой в rgbValue строки. Если размер строки не может быть определен, то по адресу pcbValue размещается SQL_NO_TOTAL. Если размер строки не может быть определен, или больше cbValueMax, то данные в rgbValue усекаются до размера, определенного в cbValueMax и имеют нулевое окончание, благодаря драйверу. Для двоичных данных выполняется то же самое с поправкой на нуль – окончание. Для всех других типов данных значение cbValueMax игнорируется и драйвер считает, что размер rgbValue равен размеру С – типа данных, определенного в fcType. |
Приведем пример программы, использующей средства ODBC:
#include <sql.h>
#include <stdio.h>
#include <stdlib.h>
#define MAX_STMT_LEN 100
main()
{
HENV henv; /*идентификатор среды*/
HDBC hdbc; /*идентификатор соединения*/
HSTMT hstmt; /*идентификатор оператора*/
RETCODE rc; /*код возврата*/
UCHAR selstmt [MAX_STMT_LEN] /*строка оператора*/
UCHAR address [30];
UCHAR tel_no [15];
UCHAR pos [25];
SDWORD address_len, tel_no_len, pos_len;
SQLAllocEnv (&henv);
SQLAllocConnect (henv, &hdbc);
rc=SQLConnect (hdbc, “drhome”, SQL_NTS, “student”, SQL_NTS, “student”,
SQL_NTS);
if (rc = = SQL_SUCCESS || rc = = SQL_SUCCESS_WITH_INFO)
{
SQLAllocStmt (hdbc,&hstmt);
lstrcpy (selstmt, “select address, tel_no, position from staff
where lname = ‘Иванов’ and fname = ‘Иван’ ”);
if (SQLExecDirect (hstmt, selstmt, SQL_NTS) != SQL_SUCCESS)
exit (-1);
SQLBindCol (hstmt, 1, SQL_C_CHAR, address,
(SDWORD)sizeof(address), address_len);
SQLBindCol (hstmt, 2, SQL_C_CHAR, tel_no,
(SDWORD)sizeof(tel_no), tel_no_len);
SQLBindCol (hstmt, 3, SQL_C_CHAR, pos,
(SDWORD)sizeof(pos), pos_len);
while(RETCODE_IS_SUCCESSFULL(rc))
{
rc=SQLFetch (hstmt);
if (RETCODE_IS_SUCCESSFULL(rc))
{
/*…вывод возвращенных строк…*/
}
}
SQLFreeStmt (hstmt, SQL_DROP);
SQLDisconnect (hdbc);
}
SQLFreeConnect (hdbc);
SQLFreeEnv(henv);
}
· Варианты заданий
1. Создать базу данных библиотека с таблицами (сотрудники, читатели, книги). Реализовать приложение позволяющее сформировать запросы по поиску подробной информации о читателе (включающем в себя количество взятых книг), о находящихся на руках книгах с возможностью определения просроченных (время, которое книга может оставаться на руках не должно превышать месяц)
2 Создать базу данных по бронированию авиа-билетов (сотрудники, рейсы, пассажиры). Реализовать приложение позволяющее формировать запросы по поиску информации об определенном рейсе, информацию о рейсах выполняющих перелет по указанному пользователем месту назначения, заказывать билеты.
3 Создать базу данных для банковских расчетов с клиентом (вкладчики , заемщики, условия кредитования и заёма). Реализовать приложение позволяющее формировать запросы по поиску полной информации о конкретном заемщики и вкладчике, подсчитывать суммы по процентным ставкам за текущий месяц, квартал, год. Позволять заносить новых вкладчиков или заемщиков.
4 Создать базу данных для предприятия (сотрудники , офисы). Создать приложение реализующее возможность подсчета сотрудников в каждом из офисов, определяющее минимальную, среднюю, суммарную зарплату сотрудников офисов, а также предоставляющую полную информацию о руководителях офисов.
5. Создать базу данных гостиничного комплекса (гостиницы, номера, сотрудники, гости). Создать приложение позволяющее бронировать номера, определять гостиницу и номер проживающего по введенному имени и фамилии. По требованию пользователя определять просроченные номера, количество дней просрочки.
6. Создать офисную базу данных. Реализовать посредством пунктов меню приложения возможности генерирования итоговых отчетов по количеству заключенных сделок за указанный период с возможностью выбора значения из списка (за прошедший год, квартал, месяц, декаду, день) либо указания произвольного периода. В отчете указывать также суммарную стоимость сделанных заказов. Выявлять сотрудников реализовавших наибольшее количество сделок за указанный период. Выявлять товары (услуги) пользующиеся максимальным спросом.
7. Создать базу данных учета поставок на предприятие. (должны быть реализованы таблицы Предприятия-поставщики, договора, поставки) Создать приложение позволяющее просматривать текущие поставки, договора с предприятиями, информацию о предприятиях-поставщиках. Предусмотреть возможность определения просроченных договоров, неосуществленных на данный момент поставок по предоплате, а также определение и предоставление информации о предприятии должнике. Помимо этого приложение должно определять задолженность по оплате поставок и пеню за каждый просроченный день.
8. Создать складскую БД. (Таблицы о имеющихся в наличии товарах и квитанциях на получение ) Написать приложение определяющее поиск и выдачу информации о количестве указанного товара и о дате поступления его на склад. Реализовать триггеры мониторинга, позволяющие отслеживать изменения таблиц БД с сохранением во временных таблицах данных о количестве товара до и после обновления, а также информацию о лице, произведшем изменение и его дате и времени. Предусмотреть вспомогательное (защищенное приложение) позволяющее заведующему просматривать вспомогательные таблицы с возможностью их анализа, т.е. приложение должно подсчитывать количество произведенных изменений на указанный товар, а также предоставлять полную информацию о произведенном изменении по указанному наименованию товара. Помимо этого данное “скрытое” приложение должно выявлять недостачи, а также предполагаемых виновников. (Для реализации этой возможности в таблице о имеющихся в наличии товарах, должны указываться дата его поступления на склад и поступившее количество, а в таблице с квитанциями на получение каждый раз фиксироваться дата и количество получаемых единиц).
9. Создать базу данных военно-учетного стола. (Таблицы о призывниках, врачах медкомиссии, результатах осмотра призывников в виде замечаний врачей и рекомендаций на дополнительное обследование). В случае отсутствия замечаний по здоровью осматривающим врачом в БД фиксируется строка “замечаний нет”, в случае необходимости дополнительного обследования фиксируется строка “необходимо дальнейшее обследование”. Приложение должно определять всех годных призывников по отсутствию замечаний всех обследующих врачей и негодных в случае любой другой отметки хотя бы одним обследующим врачом. Помимо этого приложение должно определять нуждающихся в дальнейшем обследовании призывников по соответствующим отметкам в БД и определять процент годных.
10. Создать БД для работы пунктов по покупке-продаже валюты. (Таблицы покупателей-продавцов, проведенные сделки за день, курсы валют, итоги за день) Пункт обмена занимается продажей и покупкой валюты только за белорусские рубли. Программа должна быть рассчитана на кассира, т. е. необходимо обеспечить наглядный ввод данных покупателя-продавца и данных в соответствующую таблицу БД. Программа должна фиксировать оформление сделки с указанием: типа выполняемой операции (покупка или продажа), валюты (курс определяется на основе данных о типе операции и валюты), количества и суммарного эквивалента в белорусских рублях (в случае покупки валюты за белорусские рубли) или продаваемой валюты. Количество указывается кассиром, эквивалент вычисляется на основе указанного количества и полученных данных о курсах покупки или продажи. Помимо этого необходимо реализовать скрытый процесс для периодического обновления итогов сделок, включающих в себя количество проданной и купленной валюты и рублевый эквивалент проделанных операций с сохранением высчитанной информации в файле.
11. Реализовать телефонный справочник. Базу, возможно, реализовать как единую таблицу с ключевым проиндексированным полем со значениями телефонных номеров, либо разделить номера, частных абонентов и организаций. Программа осуществляет стандартный поиск адреса организации или частного лица по указанному номеру, определяя наименования организации или ФИО частного абонента. А также поиск номера по указанному адресу с определением того, кому этот номер принадлежит, либо поиск номера по названию организации или ФИО абонента с определением адреса. Предусмотреть возможность поиска при неполной информации, т. е. поисковая информация выдается в случае ее частичного удовлетворения заданным пользователем параметрам. Например, в случае поиска по фамилии, при введенном: “Иван”,выдавать номера телефонов, принадлежащих Ивановым, Иванковским, Иванькиным, и.т.д.
Литература
1. Коннолли Т., Бегг К. Базы данных: Проектирование, реализация и сопровождение. Теория и практика. Из-во: Вильямс 2000.
2. Бобровски С. ORACLE 8: Архитектура. (Основные принципы построения и структура баз данных ORACLE) –М: Лори, 1998.
3. Урман С. ORACLE 8i: Новые возможности программирования на языке PL/SQL –М: Лори, 2001.