c mysql连接池_在LINUX下用C/C++写了一个连接池(访问MYSQL)的类
一、頭文件【存為:connPool.h】
#ifndef __CONNECTION_POOL_H__
#define __CONNECTION_POOL_H__
#include "mutex.h"
#define?MYSQL_CONN_NUM_MAX_VALUE?500
using namespace std;
enum _USE_STATUS
{
US_USE = 0,
US_IDLE = 1
};
typedef?struct _sConStatus
{
void*?connAddr;
int?useStatus;
}sConStatus;
class CConnPool
{
public:
CConnPool();
~CConnPool();
public:
int Init(string& strMysqlIp, string&?strUser, string&?strPwd, string&?strDbName, int nMysqlPort, int nConnNum);//connection?pool init
void* getOneConn();//get a connection
void?retOneConn(void* pMysql);// return a connection
void?checkConn(); // check the connection if is alive
void* createOneConn();
public:
char m_szMysqlIp[100];
char m_szUser[100];
char m_szPwd[100];
char m_szDbName[100];
int?m_nMysqlPort;?int?m_nConnNum;
public:
CMutex?m_sMutex;
vector?m_vectorConn;
map m_mapVI;
map m_mapMysqlScs;
};
class CConnPoolV2
{
public:
CConnPoolV2();
~CConnPoolV2();
public:
int Init(string& strMysqlIp, string&?strUser, string&?strPwd, string&?strDbName, int nMysqlPort, int nConnNum);//connection?pool init
void* getOneConn(); //從連接池取一個連接
void?retOneConn(void* pConn);// 連接用完了,把它放回連接池。以便其他人用。
void?checkConn(); // check the connection if is alive
void* createOneConn();
private:
string m_strMysqlIp;
string m_strUser;
string m_strPwd;
string m_strDbName;
int?m_nMysqlPort;?int?m_nConnNum;
private:
CMutex?m_sMutex;
vector?m_vectorConn;
map m_mapVI; //?從連接的地址,快速找到索引,便于存放到m_vectorConn中。
};
#endif
二、源碼【存為:connPool.cpp】
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include ?#include ?#include
#include
#include
#include
#include "mysql.h"
#include "encapsulation_mysql.h"
#include "connPool.h"
#include "mutex.h"
using namespace std;
using namespace EncapMysql;
CConnPool::CConnPool( )
{
}
CConnPool::~CConnPool( )
{
}
void* CConnPool::createOneConn()
{
MYSQL*?mysql;
mysql = mysql_init(0);
if(mysql == NULL)
{
cout << "mysql_init fail**" << endl;?return NULL;
}
if(mysql_real_connect(mysql,?m_szMysqlIp , m_szUser ,?m_szPwd,?m_szDbName?,?m_nMysqlPort, NULL,0)==NULL)
{
cout << "connect failure!" << endl;
return NULL;
}
else
{
cout << "connect success!" << endl;
}
//
return mysql;
}
int CConnPool::Init(string& strMysqlIp, string&?strUser, string&?strPwd, string&?strDbName, int nMysqlPort, int nConnNum)
{
strcpy(m_szMysqlIp, strMysqlIp.c_str());
strcpy( m_szUser, strUser.c_str());
strcpy(m_szPwd, strPwd.c_str());
strcpy(m_szDbName, strDbName.c_str());
m_nMysqlPort = nMysqlPort;?m_nConnNum = nConnNum;?MYSQL*?mysql;
for(int i=0; i
{
mysql = (MYSQL*)this->createOneConn();
if(mysql == NULL)
return -1;
//?sConStatus* scs = new sConStatus();
scs->connAddr = mysql;
scs->useStatus = US_IDLE;
m_vectorConn.push_back(scs);?m_mapVI[scs] = i;
m_mapMysqlScs[mysql] = scs;
}
m_nConnNum = nConnNum;
}
//從連接池中取一個連接,同時,給它做一個標記,表明它已經被使用,防止別的線程再使用。
void* CConnPool::getOneConn()
{
int N = m_vectorConn.size();
for(int i=0; i< N; i++)
{
CGuard?guard(m_sMutex);
sConStatus* scs = (sConStatus*)m_vectorConn[i];
if(scs->useStatus ==?US_IDLE)
{
scs->useStatus = US_USE;
return?scs->connAddr;
}?}
//
return NULL;
}
//把連接歸還給連接池。同時,給它做一個標記,表明它是空閑的,可以使用。
void?CConnPool::retOneConn(void* pMysql)
{
if(!pMysql)
return;
//?map::iterator?it1;
map::iterator it2;
CGuard?guard(m_sMutex);
it1 = m_mapMysqlScs.find(pMysql);
if(it1 == m_mapMysqlScs.end())
return;
it2 = m_mapVI.find(it1->second);
if(it2 == m_mapVI.end())
return;
int nInx = it2->second;
sConStatus* scs = (sConStatus*) m_vectorConn[nInx];
scs->useStatus = US_IDLE;
}
void?CConnPool::checkConn()
{
map::iterator?it1;
MYSQL*?mysql;
//?for(int i=0; i
{
CGuard?guard(m_sMutex);
sConStatus* scs = (sConStatus*)m_vectorConn[i];
if(scs->useStatus == US_USE)
continue;
//?mysql =(MYSQL*)(scs->connAddr);
int status=mysql_query(mysql, "select count(*) from t_user;" );
if(status != 0) //說明連接已經不可用了。
{
it1 = m_mapMysqlScs.find(mysql);
if(it1 != m_mapMysqlScs.end())
{
m_mapMysqlScs.erase(it1);
}
//
mysql_close(mysql);
//
mysql = (MYSQL*)this->createOneConn();
m_mapMysqlScs[mysql] = scs;
}
}
//
}
// 2011-01-20, 這個類這樣寫,感覺耦合性更為松散,比較好。使用起來也好理解一些。
CConnPoolV2::CConnPoolV2( )
{
}
CConnPoolV2::~CConnPoolV2( )
{
}
//創建一個連接,并設為 IDLE狀態。
void* CConnPoolV2::createOneConn()
{
try
{
CEncapMysql*?pEM = new CEncapMysql();
if(pEM == NULL)
{
printf("pEM == NULL**\r\n");?return NULL;
}?//
int nRet = pEM->Connect(m_strMysqlIp.c_str(), m_strUser.c_str(), m_strPwd.c_str());
if(nRet != 0)
{
printf("pEM->Connect fail**\r\n");?return NULL;
}?//?pEM->SetIdle();
//
return pEM;
}?catch(...)
{
printf("createOneConn?exception**\r\n");?return NULL;
}
}
//成功: 返回0
int CConnPoolV2::Init(string& strMysqlIp, string&?strUser, string&?strPwd, string&?strDbName, int nMysqlPort, int nConnNum)
{
m_strMysqlIp?= strMysqlIp;
m_strUser?= strUser;
m_strPwd?= strPwd;
m_strDbName?= strDbName;
m_nMysqlPort = nMysqlPort;?m_nConnNum = nConnNum;?CEncapMysql* pEM;
int nRet;
for(int i=0; i
{
pEM = (CEncapMysql*)this->createOneConn();
if(!pEM )
return -1;
//?m_vectorConn.push_back(pEM);?m_mapVI[pEM] = i;
}
return?0;
}
void* CConnPoolV2::getOneConn()
{
CGuard?guard(m_sMutex);
//
for(int i=0; i< m_nConnNum; i++)
{
CEncapMysql* pEM = (CEncapMysql*)m_vectorConn[i];
if( pEM->IsIdle())
{
pEM->SetUsed();
return pEM;
}?}
//可能訪問MYSQL的用戶較多,連接池中已無空閑連接了。只要總連接數沒有超限,就新建一個連接。
if(m_nConnNum < MYSQL_CONN_NUM_MAX_VALUE)
{
CEncapMysql* pEM = (CEncapMysql*)this->createOneConn();
if(!pEM )
return NULL;
//?m_vectorConn.push_back(pEM);?m_mapVI[pEM] = m_nConnNum++;
}?//
return NULL;
}
void?CConnPoolV2::retOneConn(void* pConn)
{
map::iterator it;
CGuard?guard(m_sMutex);
it = m_mapVI.find(pConn);
if(it == m_mapVI.end())
{
printf("retOneConn?fail***\n");?return;
}?int nInx = it->second;
CEncapMysql* pEM = (CEncapMysql*) m_vectorConn[nInx];
pEM->SetIdle();
printf("retOneConn?succ!\n");?}
void?CConnPoolV2::checkConn()
{
//暫時可以不實現。因為查詢失敗時,已重新連接了。
}
總結
以上是生活随笔為你收集整理的c mysql连接池_在LINUX下用C/C++写了一个连接池(访问MYSQL)的类的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 2022年办银行卡需要什么证件和材料,有
- 下一篇: mysql 查询慢 分析_MySQL优化