Учебники

MFC — База данных классов

База данных — это набор информации, которая организована таким образом, чтобы к ней можно было легко обращаться, управлять и обновлять. Классы базы данных MFC на основе ODBC предназначены для обеспечения доступа к любой базе данных, для которой доступен драйвер ODBC. Поскольку классы используют ODBC, ваше приложение может получать доступ к данным в разных форматах и ​​в разных локальных / удаленных конфигурациях.

Вам не нужно писать специальный код для работы с различными системами управления базами данных (СУБД). Пока ваши пользователи имеют соответствующий драйвер ODBC для данных, к которым они хотят получить доступ, они могут использовать вашу программу для манипулирования данными в таблицах, хранящихся там. Источник данных — это конкретный экземпляр данных, размещенный в некоторой системе управления базами данных (СУБД). Примеры включают Microsoft SQL Server, Microsoft Access и т. Д.

CDatabase

MFC предоставляет класс CDatabase, который представляет собой соединение с источником данных, с помощью которого вы можете работать с источником данных. Вы можете иметь один или несколько объектов CDatabase одновременно активными в вашем приложении.

BeginTrans

Запускает «транзакцию» — серию обратимых вызовов функций-членов AddNew, Edit, Delete и Update класса CRecordset — на подключенном источнике данных. Источник данных должен поддерживать транзакции, чтобы BeginTrans имел какой-либо эффект.

BindParameters

Позволяет связать параметры перед вызовом ExecuteSQL .

отменить

Отменяет асинхронную операцию или процесс из второго потока.

CanTransact

Возвращает ненулевое значение, если источник данных поддерживает транзакции.

CanUpdate

Возвращает ненулевое значение, если объект CDatabase является обновляемым (не только для чтения).

близко

Закрывает соединение с источником данных.

CommitTrans

Завершает транзакцию, начатую BeginTrans. Команды в транзакции, которые изменяют источник данных, выполняются.

ExecuteSQL

Выполняет инструкцию SQL. Записи данных не возвращаются.

GetBookmarkPersistence

Определяет операции, посредством которых закладки сохраняются на объектах набора записей.

GetConnect

Возвращает строку подключения ODBC, используемую для подключения объекта CDatabase к источнику данных.

GetCursorCommitBehavior

Определяет влияние совершения транзакции на объект открытого набора записей.

GetCursorRollbackBehavior

Определяет влияние отката транзакции на открытый объект набора записей.

GetDatabaseName

Возвращает имя базы данных, используемой в данный момент.

Открыт

Возвращает ненулевое значение, если объект CDatabase в настоящее время подключен к источнику данных.

OnSetOptions

Вызывается структурой для установки стандартных параметров подключения. Реализация по умолчанию устанавливает значение времени ожидания запроса. Вы можете установить эти параметры заранее, вызвав SetQueryTimeout .

открыто

Устанавливает соединение с источником данных (через драйвер ODBC).

OpenEx

Устанавливает соединение с источником данных (через драйвер ODBC).

отмена

Отменяет изменения, сделанные во время текущей транзакции. Источник данных возвращается в прежнее состояние, как определено при вызове BeginTrans, без изменений.

SetLoginTimeout

Устанавливает количество секунд, по истечении которых попытка подключения к источнику данных истекает.

SetQueryTimeout

Устанавливает количество секунд, по истечении которых операции запроса к базе данных будут задерживаться. Влияет на все последующие наборы записей Open, AddNew, Edit и Delete на вызовы.

Давайте рассмотрим простой пример, создав новое приложение на основе диалогового окна MFC.

Шаг 1 — Измените заголовок строки TODO на Извлечение данных из базы данных и перетащите одну кнопку и один элемент управления List, как показано на следующем снимке.

Получить данные из БД

Шаг 2 — Добавьте обработчик события нажатия для кнопки и управляющую переменную m_ListControl для управления списком.

Шаг 3 — У нас есть простая база данных, которая содержит одну таблицу сотрудников с несколькими записями, как показано на следующем снимке.

Стол сотрудников

Шаг 4 — Нам нужно включить следующий файл заголовков, чтобы мы могли использовать класс CDatabase.

#include "odbcinst.h"
#include "afxdb.h"

Вставить запрос

Оператор SQL INSERT INTO используется для добавления новых строк данных в таблицу в базе данных.

Шаг 1 — Чтобы добавить новые записи, мы будем использовать функцию ExecuteSQL () класса CDatabase, как показано в следующем коде.

CDatabase database;
CString SqlString;
CString strID, strName, strAge;
CString sDriver = L"MICROSOFT ACCESS DRIVER (*.mdb)";
CString sDsn;
CString sFile = L"D:\\Test.mdb";
// You must change above path if it's different
int iRec = 0;

// Build ODBC connection string
sDsn.Format(L"ODBC;DRIVER={%s};DSN='';DBQ=%s", sDriver, sFile);
TRY {
   // Open the database
   database.Open(NULL,false,false,sDsn);

   SqlString = "INSERT INTO Employees (ID,Name,age) VALUES (5,'Sanjay',69)";
   database.ExecuteSQL(SqlString);
   // Close the database
   database.Close();
}CATCH(CDBException, e) {
   // If a database exception occured, show error msg
   AfxMessageBox(L"Database error: " + em_strError);
}
END_CATCH;

Шаг 2 — Когда приведенный выше код скомпилирован и выполнен, вы увидите, что новая запись добавлена ​​в вашу базу данных.

Вставить очередь

Получить запись

Чтобы извлечь приведенную выше таблицу в приложении MFC, мы реализуем операции, связанные с базой данных, в обработчике событий кнопки, как показано в следующих шагах.

Шаг 1 — Чтобы использовать CDatabase, создайте объект CDatabase и вызовите его функцию Open (). Это откроет соединение.

Шаг 2 — Создайте объекты CRecordset для работы с подключенным источником данных, передайте конструктору набора записей указатель на ваш объект CDatabase.

Шаг 3 — После использования соединения вызовите функцию Close и уничтожьте объект CDatabase.

void CMFCDatabaseDemoDlg::OnBnClickedButtonRead() {
   // TODO: Add your control notification handler code here
   CDatabase database;
   CString SqlString;
   CString strID, strName, strAge;
   CString sDriver = "MICROSOFT ACCESS DRIVER (*.mdb)";
   CString sFile = L"D:\\Test.mdb";
   // You must change above path if it's different
   int iRec = 0;

   // Build ODBC connection string
   sDsn.Format("ODBC;DRIVER={%s};DSN='';DBQ=%s",sDriver,sFile);
   TRY {
      // Open the database
      database.Open(NULL,false,false,sDsn);

      // Allocate the recordset
      CRecordset recset( &database );

      // Build the SQL statement
      SqlString = "SELECT ID, Name, Age " "FROM Employees";

      // Execute the query
	  
      recset.Open(CRecordset::forwardOnly,SqlString,CRecordset::readOnly);
      // Reset List control if there is any data
      ResetListControl();
      // populate Grids
      ListView_SetExtendedListViewStyle(m_ListControl,LVS_EX_GRIDLINES);

      // Column width and heading
      m_ListControl.InsertColumn(0,"Emp ID",LVCFMT_LEFT,-1,0);
      m_ListControl.InsertColumn(1,"Name",LVCFMT_LEFT,-1,1);
      m_ListControl.InsertColumn(2, "Age", LVCFMT_LEFT, -1, 1);
      m_ListControl.SetColumnWidth(0, 120);
      m_ListControl.SetColumnWidth(1, 200);
      m_ListControl.SetColumnWidth(2, 200);

      // Loop through each record
      while( !recset.IsEOF() ) {
         // Copy each column into a variable
         recset.GetFieldValue("ID",strID);
         recset.GetFieldValue("Name",strName);
         recset.GetFieldValue("Age", strAge);

         // Insert values into the list control
         iRec = m_ListControl.InsertItem(0,strID,0);
         m_ListControl.SetItemText(0,1,strName);
         m_ListControl.SetItemText(0, 2, strAge);

         // goto next record
         recset.MoveNext();
      }
      // Close the database
      database.Close();
   }CATCH(CDBException, e) {
      // If a database exception occured, show error msg
      AfxMessageBox("Database error: "+em_strError);
   }
   END_CATCH; 
}

// Reset List control
void CMFCDatabaseDemoDlg::ResetListControl() {
   m_ListControl.DeleteAllItems();
   int iNbrOfColumns;
   CHeaderCtrl* pHeader = (CHeaderCtrl*)m_ListControl.GetDlgItem(0);
   if (pHeader) {
      iNbrOfColumns = pHeaderGetItemCount();
   }
   for (int i = iNbrOfColumns; i >= 0; i--) {
      m_ListControl.DeleteColumn(i);
   }
}

Шаг 4 — Вот файл заголовка.

// MFCDatabaseDemoDlg.h : header file
//

#pragma once
#include "afxcmn.h"


// CMFCDatabaseDemoDlg dialog
class CMFCDatabaseDemoDlg : public CDialogEx {
   // Construction
   public:
      CMFCDatabaseDemoDlg(CWnd* pParent = NULL);    // standard constructor

   // Dialog Data
   #ifdef AFX_DESIGN_TIME
      enum { IDD = IDD_MFCDATABASEDEMO_DIALOG };
   #endif

   protected:
      virtual void DoDataExchange(CDataExchange* pDX);    // DDX/DDV support
      void ResetListControl();

   // Implementation
   protected:
      HICON m_hIcon;

      // Generated message map functions
      virtual BOOL OnInitDialog();
      afx_msg void OnPaint();
      afx_msg HCURSOR OnQueryDragIcon();
      DECLARE_MESSAGE_MAP()
   public:
      CListCtrl m_ListControl;
      afx_msg void OnBnClickedButtonRead();
};

Шаг 5 — Когда приведенный выше код скомпилирован и выполнен, вы увидите следующий вывод.

Получить запись

Шаг 6 — Нажмите кнопку Read, чтобы выполнить операции с базой данных. Он получит таблицу сотрудников.

Получить запись

Обновить запись

Запрос SQL UPDATE используется для изменения существующих записей в таблице. Вы можете использовать предложение WHERE с запросом UPDATE для обновления выбранных строк, в противном случае все строки будут затронуты.

Шаг 1 — Давайте рассмотрим простой пример, обновив Age, где ID равен 5.

SqlString = L"UPDATE Employees SET Age = 59 WHERE ID = 5;";
database.ExecuteSQL(SqlString);

Шаг 2 — Вот полный код события нажатия кнопки.

void CMFCDatabaseDemoDlg::OnBnClickedButtonRead() {
   // TODO: Add your control notification handler code here
   CDatabase database;
   CString SqlString;
   CString strID, strName, strAge;
   CString sDriver = L"MICROSOFT ACCESS DRIVER (*.mdb)";
   CString sDsn;
   CString sFile =
      L"C:\\Users\\Muhammad.Waqas\\Downloads\\Compressed\\ReadDB_demo\\Test.mdb";
   // You must change above path if it's different
   int iRec = 0;

   // Build ODBC connection string
   sDsn.Format(L"ODBC;DRIVER={%s};DSN='';DBQ=%s", sDriver, sFile);
   TRY {
      // Open the database
      database.Open(NULL,false,false,sDsn);

      // Allocate the recordset
      CRecordset recset(&database);

      SqlString = L"UPDATE Employees SET Age = 59 WHERE ID = 5;";

      database.ExecuteSQL(SqlString);

      SqlString = "SELECT ID, Name, Age FROM Employees";

      // Build the SQL statement
      SqlString = "SELECT ID, Name, Age FROM Employees";

      // Execute the query
      recset.Open(CRecordset::forwardOnly,SqlString,CRecordset::readOnly);

      // Reset List control if there is any data
      ResetListControl();
      // populate Grids
      ListView_SetExtendedListViewStyle(m_listCtrl,LVS_EX_GRIDLINES);

      // Column width and heading
      m_listCtrl.InsertColumn(0,L"Emp ID",LVCFMT_LEFT,-1,0);
      m_listCtrl.InsertColumn(1,L"Name",LVCFMT_LEFT,-1,1);
      m_listCtrl.InsertColumn(2, L"Age", LVCFMT_LEFT, -1, 1);
      m_listCtrl.SetColumnWidth(0, 120);
      m_listCtrl.SetColumnWidth(1, 200);
      m_listCtrl.SetColumnWidth(2, 200);

      // Loop through each record
      while (!recset.IsEOF()) {
         // Copy each column into a variable
         recset.GetFieldValue(L"ID",strID);
         recset.GetFieldValue(L"Name",strName);
         recset.GetFieldValue(L"Age", strAge);

         // Insert values into the list control
         iRec = m_listCtrl.InsertItem(0,strID,0);
         m_listCtrl.SetItemText(0,1,strName);
         m_listCtrl.SetItemText(0, 2, strAge);

         // goto next record
         recset.MoveNext();
      }

      // Close the database
      database.Close();
   }CATCH(CDBException, e) {
      // If a database exception occured, show error msg
      AfxMessageBox(L"Database error: " + em_strError);
   }
   END_CATCH;
}

Шаг 3 — Когда приведенный выше код скомпилирован и выполнен, вы увидите следующий вывод.

Получить запись

Шаг 4 — Нажмите кнопку Read, чтобы выполнить операции с базой данных. Он получит следующую таблицу сотрудников.

Обновить запись

Шаг 5 — Теперь вы можете видеть, что возраст обновлен с 69 до 59 лет.

Удалить запись

Запрос SQL DELETE используется для удаления существующих записей из таблицы. Вы можете использовать предложение WHERE с запросом DELETE для удаления выбранных строк, в противном случае все записи будут удалены.

Шаг 1 — Давайте рассмотрим простой пример, удалив запись, где ID равен 3.

SqlString = L"DELETE FROM Employees WHERE ID = 3;";

database.ExecuteSQL(SqlString);

Шаг 2 — Вот полный код события нажатия кнопки.

void CMFCDatabaseDemoDlg::OnBnClickedButtonRead() {
   // TODO: Add your control notification handler code here
   CDatabase database;
   CString SqlString;
   CString strID, strName, strAge;
   CString sDriver = L"MICROSOFT ACCESS DRIVER (*.mdb)";
   CString sDsn;
   CString sFile =
       L"C:\\Users\\Muhammad.Waqas\\Downloads\\Compressed\\ReadDB_demo\\Test.mdb";

   // You must change above path if it's different
   int iRec = 0;

   // Build ODBC connection string
   sDsn.Format(L"ODBC;DRIVER={%s};DSN='';DBQ=%s", sDriver, sFile);
   TRY {
      // Open the database
      database.Open(NULL,false,false,sDsn);

      // Allocate the recordset
      CRecordset recset(&database);

      SqlString = L"DELETE FROM Employees WHERE ID = 3;";

      database.ExecuteSQL(SqlString);

      SqlString = "SELECT ID, Name, Age FROM Employees";

      // Build the SQL statement
      SqlString = "SELECT ID, Name, Age FROM Employees";

      // Execute the query
      recset.Open(CRecordset::forwardOnly,SqlString,CRecordset::readOnly);

      // Reset List control if there is any data
      ResetListControl();
      // populate Grids
      ListView_SetExtendedListViewStyle(m_listCtrl,LVS_EX_GRIDLINES);
      // Column width and heading
      m_listCtrl.InsertColumn(0,L"Emp ID",LVCFMT_LEFT,-1,0);
      m_listCtrl.InsertColumn(1,L"Name",LVCFMT_LEFT,-1,1);
      m_listCtrl.InsertColumn(2, L"Age", LVCFMT_LEFT, -1, 1);
      m_listCtrl.SetColumnWidth(0, 120);
      m_listCtrl.SetColumnWidth(1, 200);
      m_listCtrl.SetColumnWidth(2, 200);

      // Loop through each record
      while (!recset.IsEOF()) {
         // Copy each column into a variable
         recset.GetFieldValue(L"ID",strID);
         recset.GetFieldValue(L"Name",strName);
         recset.GetFieldValue(L"Age", strAge);

         // Insert values into the list control
         iRec = m_listCtrl.InsertItem(0,strID,0);
         m_listCtrl.SetItemText(0,1,strName);
         m_listCtrl.SetItemText(0, 2, strAge);

         // goto next record
         recset.MoveNext();
      }
      // Close the database
      database.Close();
   }CATCH(CDBException, e) {
      // If a database exception occured, show error msg
      AfxMessageBox(L"Database error: " + em_strError);
   }
   END_CATCH;
}

Шаг 3 — Когда приведенный выше код скомпилирован и выполнен, вы увидите следующий вывод.

Получить запись

Шаг 4 — Нажмите кнопку Read, чтобы выполнить операции с базой данных. Он получит таблицу сотрудников.