mysql,redis客户端连接池和线程池的Linux C编程实现(★firecat推荐★)

本文涉及的产品
云数据库 Tair(兼容Redis),内存型 2GB
云数据库 RDS MySQL,集群系列 2核4GB
推荐场景:
搭建个人博客
Redis 开源版,标准版 2GB
推荐场景:
搭建游戏排行榜
简介: mysql,redis客户端连接池和线程池的Linux C编程实现(★firecat推荐★)

一、环境准备:


CentOS7,CMake编译器


Mysql使用官方c语言版本客户端,不使用c++库,因为c++库依赖boost库


Linux安装mysql时,有这个包,mysql-community-devel-5.7.18-1.el7.x86_64.rpm -- 里面内容是c语言版本的客户端库函数和头文件


https://downloads.mysql.com/archives/community/


Redis使用自带的hiredis库,也是c语言实现


https://github.com/antirez/redis/tree/unstable/deps/hiredis


https://github.com/redis/hiredis




二、完整的工程源码:https://download.csdn.net/download/libaineu2004/10300017




CMakeLists.txt


cmake_minimum_required(VERSION 2.8)

#工程主要参考TeamTalk

#https://github.com/meili/TeamTalk/tree/master/server/src/db_proxy_server

PROJECT(mysqlredis_pool)

AUX_SOURCE_DIRECTORY(. SRC_LIST)

#mysql客户端,我们不使用c++版本,因为它依赖boost库,太啰嗦

#mysql-connector-c++-1.1.8-linux-el7-x86-64bit.tar.gz -- https://downloads.mysql.com/archives/c-cpp/

#推荐使用c版本 -- https://downloads.mysql.com/archives/c-c/

#mysql-community-devel-5.7.18-1.el7.x86_64.rpm 自带了c语言客户端头文件和库

#安装说明 -- http://blog.csdn.net/libaineu2004/article/details/76212125

SET(MYSQL_INCLUDE_DIR /usr/include/mysql)

SET(MYSQL_LIB /usr/lib64/mysql)

#redis客户端,使用c版本 -- https://github.com/redis/hiredis

#安装说明 -- http://blog.csdn.net/libaineu2004/article/details/76209267

SET(REDIS_INCLUDE_DIR /usr/local/include/hiredis/)

SET(REDIS_LIB /usr/local/lib/)

INCLUDE_DIRECTORIES(${MYSQL_INCLUDE_DIR} ${REDIS_INCLUDE_DIR})

LINK_DIRECTORIES(${MYSQL_LIB} ${REDIS_LIB})

#ADD_EXECUTABLE必须在TARGET_LINK_LIBRARIES前面,否则会报错

ADD_EXECUTABLE(${PROJECT_NAME} ${SRC_LIST})

TARGET_LINK_LIBRARIES(${PROJECT_NAME} mysqlclient hiredis pthread)



main.cpp

#include "DBPool.h"
#include "CachePool.h"
#include "ThreadPool.h"
#include "ProxyTask.h"
#include <stdio.h>
#include <stdlib.h>
#include <signal.h>
#include <fcntl.h> //daemonize
#include <string>
#include <string.h>
void handler(uint32_t conn_uuid)
{
    printf("hello,%d\n", conn_uuid);
    CDBManager* pDBManger = CDBManager::getInstance();
    if (!pDBManger) {
        printf("DBManager init failed");
        return;
    }
    CDBConn* pDBConn = pDBManger->GetDBConn("teamtalk_master");//get a db conn
    if (pDBConn) {
        string strSql = "select * from IMUser";
        CResultSet* pResultSet = pDBConn->ExecuteQuery(strSql.c_str());
        if (pResultSet)
        {
            delete pResultSet;
        }
        pDBManger->RelDBConn(pDBConn);//注意,con用完之后一定要记得归还,ReleaseConnection
    }
}
int main(int argc, char* argv[])
{
    signal(SIGPIPE, SIG_IGN);
    //案例1,仅仅使用mysql连接池,不使用线程池
    CDBManager* pDBManger = CDBManager::getInstance();
    if (!pDBManger) {
        printf("DBManager init failed");
        return -1;
    }
    CDBConn* pDBConn = pDBManger->GetDBConn("teamtalk_master");//get a db conn
    if (pDBConn) {
        string strSql = "select * from IMUser";
        CResultSet* pResultSet = pDBConn->ExecuteQuery(strSql.c_str());
        if (pResultSet)
        {
            string strResult, strSalt;
            uint32_t nId, nGender, nDeptId, nStatus;
            string strNick, strAvatar, strEmail, strRealName, strTel, strDomain,strSignInfo;
            while (pResultSet->Next()) {
                nId = pResultSet->GetInt("id");
                strResult = pResultSet->GetString("password");
                strSalt = pResultSet->GetString("salt");
                strNick = pResultSet->GetString("nick");
                nGender = pResultSet->GetInt("sex");
                strRealName = pResultSet->GetString("name");
                strDomain = pResultSet->GetString("domain");
                strTel = pResultSet->GetString("phone");
                strEmail = pResultSet->GetString("email");
                strAvatar = pResultSet->GetString("avatar");
                nDeptId = pResultSet->GetInt("departId");
                nStatus = pResultSet->GetInt("status");
                strSignInfo = pResultSet->GetString("sign_info");
            }
            delete pResultSet;
        }
        pDBManger->RelDBConn(pDBConn);//注意,con用完之后一定要记得归还,ReleaseConnection
    }
    //案例2,使用mysql连接池,也使用线程池
    //top -H -p <pid> 终端查看某个特定进程<pid>并检查该进程内运行的线程状况
    CThreadPool thread_pool;
    thread_pool.Init(10);
    CTask* pTask1 = new CProxyTask(1, handler);//void CWorkerThread::Execute()执行完任务会删除指针CTask*
    thread_pool.AddTask(pTask1);
    CTask* pTask2 = new CProxyTask(2, handler);
    thread_pool.AddTask(pTask2);
    CTask* pTask3 = new CProxyTask(3, handler);
    thread_pool.AddTask(pTask3);
    //案例3,仅仅使用redis连接池,不使用线程池
    CacheManager* pCacheManager = CacheManager::getInstance();
    if (!pCacheManager) {
        printf("CacheManager init failed");
        return -1;
    }
    CacheConn* pCacheConn = pCacheManager->GetCacheConn("redis");
    if (pCacheConn)
    {
        string strVal = "sodesiname";
        pCacheConn->set("total_user_update", strVal);
        string str = pCacheConn->get("total_user_update");
        printf("%s\n", str.c_str());
        pCacheManager->RelCacheConn(pCacheConn);
    }
    //进程挂起,等待任务执行完成
    printf("\ninput:\n");
    char s[20];
    gets(s);  //等待输入字符串直到回车结束
    return 0;
}

姊妹篇:mysql,redis客户端连接池和线程池的Windows C/C++编程实现(★firecat推荐★)

相关实践学习
基于Redis实现在线游戏积分排行榜
本场景将介绍如何基于Redis数据库实现在线游戏中的游戏玩家积分排行榜功能。
云数据库 Redis 版使用教程
云数据库Redis版是兼容Redis协议标准的、提供持久化的内存数据库服务,基于高可靠双机热备架构及可无缝扩展的集群架构,满足高读写性能场景及容量需弹性变配的业务需求。 产品详情:https://www.aliyun.com/product/kvstore &nbsp; &nbsp; ------------------------------------------------------------------------- 阿里云数据库体验:数据库上云实战 开发者云会免费提供一台带自建MySQL的源数据库&nbsp;ECS 实例和一台目标数据库&nbsp;RDS实例。跟着指引,您可以一步步实现将ECS自建数据库迁移到目标数据库RDS。 点击下方链接,领取免费ECS&amp;RDS资源,30分钟完成数据库上云实战!https://developer.aliyun.com/adc/scenario/51eefbd1894e42f6bb9acacadd3f9121?spm=a2c6h.13788135.J_3257954370.9.4ba85f24utseFl
相关文章
|
18天前
|
NoSQL Redis 数据安全/隐私保护
Redis 最流行的图形化界面下载及使用超详细教程(带安装包)! redis windows客户端下载
文章提供了Redis最流行的图形化界面工具Another Redis Desktop Manager的下载及使用教程,包括如何下载、解压、连接Redis服务器以及使用控制台和查看数据类型详细信息。
53 6
Redis 最流行的图形化界面下载及使用超详细教程(带安装包)! redis windows客户端下载
|
18天前
|
NoSQL Redis 数据库
Redis 图形化界面下载及使用超详细教程(带安装包)! redis windows下客户端下载
文章提供了Redis图形化界面工具的下载及使用教程,包括如何连接本地Redis服务器、操作键值对、查看日志和使用命令行等功能。
59 0
Redis 图形化界面下载及使用超详细教程(带安装包)! redis windows下客户端下载
|
28天前
|
Shell Linux
Linux shell编程学习笔记30:打造彩色的选项菜单
Linux shell编程学习笔记30:打造彩色的选项菜单
|
1天前
|
监控 NoSQL 安全
如何在 Redis 中正确使用多线程?
【10月更文挑战第16天】正确使用 Redis 多线程需要综合考虑多个因素,并且需要在实践中不断摸索和总结经验。通过合理的配置和运用,多线程可以为 Redis 带来性能上的提升,同时也要注意避免可能出现的问题,以保障系统的稳定和可靠运行。
6 2
|
1天前
|
存储 NoSQL Redis
Redis 新版本引入多线程的利弊分析
【10月更文挑战第16天】Redis 新版本引入多线程是一个具有挑战性和机遇的改变。虽然多线程带来了一些潜在的问题和挑战,但也为 Redis 提供了进一步提升性能和扩展能力的可能性。在实际应用中,我们需要根据具体的需求和场景,综合评估多线程的利弊,谨慎地选择和使用 Redis 的新版本。同时,Redis 开发者也需要不断努力,优化和完善多线程机制,以提供更加稳定、高效和可靠的 Redis 服务。
6 1
|
6天前
|
Java 关系型数据库 MySQL
【编程基础知识】Eclipse连接MySQL 8.0时的JDK版本和驱动问题全解析
本文详细解析了在使用Eclipse连接MySQL 8.0时常见的JDK版本不兼容、驱动类错误和时区设置问题,并提供了清晰的解决方案。通过正确配置JDK版本、选择合适的驱动类和设置时区,确保Java应用能够顺利连接MySQL 8.0。
41 1
|
14天前
|
存储 消息中间件 NoSQL
Redis 入门 - C#.NET Core客户端库六种选择
Redis 入门 - C#.NET Core客户端库六种选择
48 8
|
10天前
|
存储 运维 NoSQL
Redis为什么最开始被设计成单线程而不是多线程
总之,Redis采用单线程设计是基于对系统特性的深刻洞察和权衡的结果。这种设计不仅保持了Redis的高性能,还确保了其代码的简洁性、可维护性以及部署的便捷性,使之成为众多应用场景下的首选数据存储解决方案。
22 1
|
18天前
|
NoSQL Redis 数据库
Redis单线程模型 redis 为什么是单线程?为什么 redis 单线程效率还能那么高,速度还能特别快
本文解释了Redis为什么采用单线程模型,以及为什么Redis单线程模型的效率和速度依然可以非常高,主要原因包括Redis操作主要访问内存、核心操作简单、单线程避免了线程竞争开销,以及使用了IO多路复用机制epoll。
35 0
Redis单线程模型 redis 为什么是单线程?为什么 redis 单线程效率还能那么高,速度还能特别快
|
27天前
|
Shell Linux
Linux shell编程学习笔记82:w命令——一览无余
Linux shell编程学习笔记82:w命令——一览无余