VC++6.0通过MFC 创建了 对话框 ,然后怎样通过SQL Server 连接到数据库?
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了VC++6.0通过MFC 创建了 对话框 ,然后怎样通过SQL Server 连接到数据库?相关的知识,希望对你有一定的参考价值。
我用VC++创建了几个关联的对话框,然后我想连接到SQL Server数据库,该怎么办?我已经创建了一个数据库Library ,数据源也已经配置好了。
class DBConnectionpublic:
DBConnection(void);
~DBConnection(void);
int OpenConnect(void);
int ExecuteSQL(_bstr_t strCmd);
_RecordsetPtr GetRecondSetPrt();
private:
_ConnectionPtr m_pConnection; //链接数据库德指针变量
_RecordsetPtr m_pRecordset; //指向记录集的指针
_variant_t RecordsAffected; //受影响的记录条数
;
DBConnection::DBConnection(void)
m_pConnection=NULL;
m_pRecordset=NULL;
DBConnection::~DBConnection(void)
m_pConnection=NULL;
m_pRecordset=NULL;
//打开数据库链接
int DBConnection::OpenConnect(void)
try
//创建连接对象
m_pConnection.CreateInstance("ADODB.Connection");
//设置连接字符串
_bstr_t strConnect ="Provider=SQLOLEDB;Data Source=20110121-1545\\SQLEXPRESS;\
Initial Catalog=ExpManDB;User ID=sa;PWD=123";
//设置连接超时时间为5秒
m_pConnection->ConnectionTimeout = 5;
//连接数据库
m_pConnection->Open(strConnect, "", "", adModeUnknown);
return 1;
catch(_com_error e)
CString errorMsg;
errorMsg.Format(_T("连接数据库失败!\r错误信息:%s"),(LPCSTR)e.ErrorMessage());
AfxMessageBox(errorMsg);
return 0;
//返回受影响的记录条数
int DBConnection::ExecuteSQL(_bstr_t strCmd)
if(m_pConnection->State)
try
m_pRecordset.CreateInstance("ADODB.Recordset"); //为Recordset对象创建实例
//执行SQL语句,并返回受影响的记录条数
m_pRecordset=m_pConnection->Execute(strCmd,&RecordsAffected,adCmdText);
return RecordsAffected.intVal;
catch(_com_error &e)
AfxMessageBox(e.Description());
return 0;
return 0;
//返回记录集以便后续使用
_RecordsetPtr DBConnection::GetRecondSetPrt()
return m_pRecordset;
可以像这样使用,strCmd为sql语句
DBConnection dbConnector;
if(dbConnector.OpenConnect() == 0)
return;
if(dbConnector.ExecuteSQL((_bstr_t)strCmd) == 0)
return;
当然如果你还需要取出数据的时候可以这样用
_RecordsetPtr pRecordSet;
pRecordSet=dbConnector.GetRecondSetPrt();
_variant_t vCardNo;
vCardNo = pRecordSet->GetCollect("cardNO"); //得到数据表种cardNO字段
后面_variant_t类型就可以转换为int float CString等各种类型了。
如果有什么问题再交流。 参考技术A 你可以创建一个数据连接的公共类:DataBase
这样就很方便在其它类来使用它了。
DataBase::DataBase()
DataBase::~DataBase()
void DataBase::ConnectDB()//创建连接
::CoInitialize(NULL);
try
m_pConnection.CreateInstance("ADODB.Connection");///创建Connection对象
_bstr_t str = "Provider=SQLOLEDB.1;Integrated Security=SSPI;Persist Security Info=False;Initial Catalog=Library ;";//Library是你的数据库名
this->m_pConnection->Open(str, "sa", "sa", adModeUnknown);
catch(_com_error e)
AfxMessageBox("connect error!");
bool DataBase::ExecuteQuery(CString sql)//执行查询
_bstr_t bSql = sql;
try
this->m_pRecordset = m_pConnection->Execute(bSql,NULL,adCmdText);
catch(_com_error e)
//AfxMessageBox("Recordset error!");
return false;
return true;
bool DataBase::Close()
return (!FAILED(m_pRecordset->Close()));
在其它类调用时:DataBase db;
db.ConnectDB();
CString sql = "select * from xxTable";
db.ExecuteQuery(sql);
db.Close(); 参考技术B LINUX / ODBC / mysql
#ifdef WIN32
#include <windows.h>
#include <odbcinst.h>
#include <sqlext.h>
#else
#include <mysql.h>
#include <unistd.h>
#define SQLHANDLE static MYSQL
#endif
#include <stdarg.h>
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
SQLHANDLE hDBEnv, hDBC;
int DB_Open(char * dbcn, char * usr, char * pwd)
int r;
#ifdef WIN32
r = SQLAllocHandle(SQL_HANDLE_ENV, SQL_NULL_HANDLE, &hDBEnv);
if(r) return 0;
r = SQLSetEnvAttr(hDBEnv,SQL_ATTR_ODBC_VERSION,
(void*)SQL_OV_ODBC3,0);
if(r) return 0;
r = SQLAllocHandle(SQL_HANDLE_DBC, hDBEnv, &hDBC);
if(r) return 0;
r = SQLConnect(hDBC,
(unsigned char *)dbcn, strlen(dbcn),
(unsigned char *)usr, strlen(usr),
(unsigned char *)pwd, strlen(pwd));
return r==SQL_SUCCESS || r==SQL_SUCCESS_WITH_INFO;
#else
mysql_init(&hDBC);
MYSQL * rx = mysql_real_connect(
&hDBC, dbcn, usr, pwd, NULL, 0, NULL, 0);
if(!rx) return 0;
return 1;
#endif
//end DB_Open
int DB_Exec(char * sql)
#ifdef WIN32
SQLHANDLE hStatement = NULL;
SQLAllocHandle(SQL_HANDLE_STMT, hDBC, &hStatement);
SQLExecDirect(hStatement,(unsigned char *)sql, strlen(sql));
SQLCloseCursor(hStatement);
SQLFreeHandle(SQL_HANDLE_STMT, hStatement);
hStatement = NULL;
#else
mysql_real_query (&hDBC, sql, strlen(sql));
#endif
return 1;
//end DB_Exec
int DB_Close(void)
#ifdef WIN32
SQLDisconnect(hDBC);
SQLFreeHandle(SQL_HANDLE_DBC, hDBC);
SQLFreeHandle(SQL_HANDLE_ENV, hDBEnv);
#else
mysql_close(&hDBC);
#endif
return 1;
//DB_Close()
#ifndef WIN32
typedef struct tagMySQLRecordset
MYSQL_RES * hRecord;
void * * row;
int * size;
int cols;
MYSQLRecordset;
#endif
void DB_CleanQuery(void *hRecordset)
if(!hRecordset) return;
#ifdef WIN32
__try
SQLCloseCursor(hRecordset);
SQLFreeHandle(SQL_HANDLE_STMT, hRecordset);
hRecordset = NULL;
__finally
return;
//end try
#else
MYSQLRecordset * hRec = (MYSQLRecordset *) hRecordset;
mysql_free_result (hRec->hRecord);
free(hRec->row); hRec->row = NULL;
free(hRec->size); hRec->size = NULL;
free(hRec); hRec = NULL;
#endif
//end DB_CleanQuery
int DB_Next(void * hRecordset)
int r=0; if(!hRecordset) return 0;
#ifdef WIN32
r = SQLFetch(hRecordset);
r = r == SQL_SUCCESS || r == SQL_SUCCESS_WITH_INFO;
if(!r)
DB_CleanQuery(hRecordset);
//end if
#else
MYSQLRecordset * hRec = (MYSQLRecordset *) hRecordset;
MYSQL_ROW row = mysql_fetch_row (hRec->hRecord);
if(row)
for(int i=0; i<hRec->cols; i++)
memcpy(hRec->row[i], row[i], hRec->size[i]);
//next i
r = 1;
else
DB_CleanQuery(hRecordset);
r = 0;
//end if
#endif
return r;
//end DB_Next
int DB_params_count(const char * fmt)
int i=0, j=0;
while(fmt[i])
if(fmt[i]=='%') j++;
i++;
//end while
return j;
//end DB_params_count
void * DB_Query(char *sql, const char *fmt, ...)
int r=0;
int cols = DB_params_count(fmt);
if(cols<1) return NULL;
#ifdef WIN32
SQLHANDLE hStatement = NULL;
SQLAllocHandle(SQL_HANDLE_STMT, hDBC, &hStatement);
r = SQLExecDirect(hStatement,(unsigned char *)sql, strlen(sql));
r = r==SQL_SUCCESS || r == SQL_SUCCESS_WITH_INFO;
if(!r)
return NULL;
//end if
#else
r = mysql_real_query (&hDBC, sql, strlen(sql));
if(r) return NULL;
MYSQL_RES * rec = NULL;
rec = mysql_store_result (&hDBC);
if(!rec) return NULL;
MYSQLRecordset * hStatement
= (MYSQLRecordset *)malloc(sizeof(MYSQLRecordset));
if(!hStatement) return NULL;
memset(hStatement, 0, sizeof(MYSQLRecordset));
hStatement->hRecord = rec;
hStatement->cols = cols;
hStatement->row = (void **)malloc(cols * sizeof(void *));
memset(hStatement->row, 0, cols * sizeof(void *));
hStatement->size = (int *)malloc(cols * sizeof(int));
memset(hStatement->size, 0, cols * sizeof(int));
#endif
va_list ap; va_start(ap, fmt);
void * var; char buf[32];
int i=0,j=0,k=0,sz=0; char c=0;
int len = strlen(fmt); int bad=1;
#ifdef WIN32
int col=1;
#else
int col=0;
#endif
while(fmt[i])
c = fmt[i++];
if(c != '%') continue;
c = fmt[i++];
var = va_arg(ap, void *);
if(c == 'd')
#ifdef WIN32
SQLBindCol(hStatement, col, SQL_C_SLONG, var, 4,NULL);
#else
hStatement->row[col] = var;
hStatement->size[col] = sizeof(long);
#endif
col++;
continue;
//end if
if(c == 'f')
#ifdef WIN32
SQLBindCol(hStatement, col, SQL_C_FLOAT, var, 4,NULL);
#else
hStatement->row[col] = var;
hStatement->size[col] = sizeof(float);
#endif
col++;
continue;
//end if
memset(buf, 0, 32); bad=1;
for(j=i-1; j<len; j++)
c = fmt[j];
if(c>='0' && c<='9') buf[j-i+1]=c;
if(c=='s')
//next j
if(bad) return NULL;
sscanf(buf, "%d", &sz);
#ifdef WIN32
SQLBindCol(hStatement, col, SQL_C_CHAR, var, sz, NULL);
#else
hStatement->row[col] = var;
hStatement->size[col] = sz;
#endif
col++;
i = k;
//end while
va_end(ap);
return hStatement;
//end DB_Rec
创建线程会在终止时挂起 MFC 对话框应用程序
【中文标题】创建线程会在终止时挂起 MFC 对话框应用程序【英文标题】:Creating a thread hangs MFC dialog app on termination 【发布时间】:2010-07-19 03:51:27 【问题描述】:我已经缩小了一个问题的范围。
-
我创建了一个简单的对话框应用程序
VC++ 6.0。
我在主线程之前启动了一个线程
对话框 DoModal() 被调用
我退出应用程序 - 有时
应用程序立即关闭,
其他时候它会挂起 10 秒
左右
这是什么原因造成的?我试过 _beginthread()、_beginthreadex() 和 AfxBeginThread()。他们都做同样的事情。
如果我在 DoModal() 调用之后添加 Sleep(50)(当 GUI 完成处理时),程序似乎每次都会毫无问题地终止。
使我缩小这个问题的原因是我有一个 Win32 DLL 可以做同样的事情。我的 DLL 有一个线程,我注意到使用这个 DLL 的应用程序有时需要一段时间才能停止。消除 DLL 并创建最简单的程序会产生相同的结果 - 这就是我上面所描述的。
以下是我添加到沼泽标准 MFC 对话框应用程序中的代码:
UINT Thread( void * )
for( ;; )
Sleep( 50 );
AfxEndThread( 0 );
return 0;
/////////////////////////////////////////////////////////////////////////////
// CThreadTest2App initialization
BOOL CThreadTest2App::InitInstance()
AfxEnableControlContainer();
// Standard initialization
// If you are not using these features and wish to reduce the size
// of your final executable, you should remove from the following
// the specific initialization routines you do not need.
#ifdef _AFXDLL
Enable3dControls(); // Call this when using MFC in a shared DLL
#else
Enable3dControlsStatic(); // Call this when linking to MFC statically
#endif
AfxBeginThread( Thread, 0 );
CThreadTest2Dlg dlg;
m_pMainWnd = &dlg;
int nResponse = dlg.DoModal();
//Sleep( 50 ); // Works when I add this ?????
if (nResponse == IDOK)
else if (nResponse == IDCANCEL)
// Since the dialog has been closed, return FALSE so that we exit the
// application, rather than start the application's message pump.
return FALSE;
有人可以帮我正确关闭我的应用程序吗?我最终想要做的是提供一种让我的 DLL 关闭的方法,而无需通过调用应用程序明确告知它停止 thead。
谢谢 保罗
【问题讨论】:
【参考方案1】:好吧,你的线程函数中有无限循环,永远不会调用AfxEndThread
!
如果你想从外部停止线程,你必须在其中编写一个信号机制,如果你必须停止,检查循环内部。
【讨论】:
好的 - 那么为什么会有所不同呢?您在线程内添加一个标志测试并在对话框完成后设置标志 - 您将遇到同样的问题。可能需要执行 3-4 次才能明白我的意思,但请试一试。 但目前你的线程被操作系统杀死,而不是你自己。这可能会因需要的时间而异。以上是关于VC++6.0通过MFC 创建了 对话框 ,然后怎样通过SQL Server 连接到数据库?的主要内容,如果未能解决你的问题,请参考以下文章