前言

在前文LMDB简介的基础上,本文介绍LMDB数据库的基本用法,包括环境environment创建、数据存储put、数据读取get等;

源码

ULONG cvtest_Test4_Lmdb()
{   INT iRet;MDB_txn *pstTxn = NULL;MDB_dbi stDbi;UINT uiKey = 1;UINT uiData = 100;iRet = mdb_env_create(&g_pstMdbEnv);if (0 != iRet){return ERROR_FAILED;}mdb_env_set_maxreaders(g_pstMdbEnv, 1);mdb_env_set_mapsize(g_pstMdbEnv, 4096 * 4096);if (ERROR_SUCCESS != Lib_CreateDir(CVTEST_LMDB_PATH)){mdb_env_close(g_pstMdbEnv);return ERROR_FAILED;}iRet = mdb_env_open(g_pstMdbEnv, CVTEST_LMDB_PATH, MDB_WRITEMAP, 0);E(iRet, "Env open failed...");iRet += mdb_txn_begin(g_pstMdbEnv, NULL, 0, &pstTxn);E(iRet, "Txm begin open failed...");iRet += mdb_dbi_open(pstTxn, NULL, MDB_CREATE, &stDbi);E(iRet, "dbi_open failed...");MDB_val stKey;MDB_val stData;stKey.mv_size = sizeof(UINT);stKey.mv_data = (VOID *)&uiKey;/* mdb_put  存数据 */stData.mv_size = sizeof(UINT);stData.mv_data = (VOID *)&uiData;iRet = mdb_put(pstTxn, stDbi, &stKey, &stData, 0);if (iRet != MDB_SUCCESS){printf("mdb_put failed : %s\n", mdb_strerror(iRet));mdb_env_close(g_pstMdbEnv);return ERROR_FAILED;}mdb_txn_commit(pstTxn);/* 重新begin一个事务---进行读 */MDB_txn *pstReadTxn = NULL;MDB_dbi stDbiRead;MDB_val stReadValue;    CHAR szBuf[BUF_LEN_100] = {0, };stReadValue.mv_size = BUF_LEN_100;stReadValue.mv_data = (VOID *)szBuf;mdb_txn_begin(g_pstMdbEnv, NULL, MDB_RDONLY, &pstReadTxn);iRet = mdb_dbi_open(pstReadTxn, NULL, 0, &stDbiRead);iRet += mdb_get(pstReadTxn, stDbiRead, &stKey, &stReadValue);if (iRet != MDB_SUCCESS){printf("mdb_get failed : %s\n", mdb_strerror(iRet));return ERROR_FAILED;}printf("stReadValue.data is %d \n", *(UINT *)stReadValue.mv_data);return ERROR_SUCCESS;
}

源码解读

  1. 按照LMDB官方介绍文档,先通过mdb_env_create创建env,后续mdb_env_set_maxreaders、mdb_env_set_mapsize设置环境相关参数;
  2. Lib_CreateDir用于创建数据库的目录,官方文档有提及:mdb_env_open参数2并不会为用户创建相关目录,因而需要提前创建;
  3. mdb_env_open、mdb_txn_begin、mdb_dbi_open分别用于打开environment、打开一个事务、打开一个数据库instance。其中mdb_dbi_open通过不同的数据库名(param 2)支持多实例
  4. mdb_put用于存入相关数据:key/value对,key/value都是MDB_val结构;
  5. 后续mdb_get用户获取数据,key与put时的key相同,get成功后,我们通过强制类型转换取得数据库内的值并打印;
  6. E是笔者封装的一个宏定义,用于检查API的返回结果,如下:
#define E(Rest, expr) LMDB_CHECK((Rest) == MDB_SUCCESS, #expr)
#define LMDB_CHECK(test, msg) ((test) ? (void)0 : ((void)fprintf(stderr, \"%s:%d: %s: %s\n", __FILE__, __LINE__, msg, mdb_strerror(test)), abort()))

测试结果

最后,我们将程序编译/得到,得到如下结果。

在相关目录产生数据文件和锁文件。

zglinux cvtest # ls -lrth /home/zhaogang/code_my/lmdb/
total 32K
---------- 1 root root 192 5月  27 21:29 lock.mdb
---------- 1 root root 16M 5月  27 21:29 data.mdb
zglinux cvtest #

结果表明:测试正确。

扩展说明

  1. LMDB通过DBI区分不同的数据库实例,支持在一个数据文件中存储多个数据库实例;
  2. LMDB是一个轻量级的开源数据库library,常用在硬件受限的嵌入式环境,不支持SQL语句
  3. LMDB通过mmap将文件映射到进程的虚拟地址空间,可加速数据库的访问;
  4. LMDB采用B+树算法存储数据,通过游标cursor可方便的访问不同位置的数据;
  5. LMDB的数据存/取都采用c语言中通用的void类型,其类型解析由程序员自行处理,提供更大的灵活性

总结

LMDB全部源码12K行,想要进一步了解其实现的读者可以参阅其源码。源码中也提供mtest、mtest2~mtest6等多个测试案例供参阅。

LMDB:轻量级内存映射数据库-----入门使用1相关推荐

  1. Python使用LMDB(闪电内存映射数据库)

    LMDB,全称Lightning Memory-Mapped Database.直译过来就是,闪电内存映射数据库. 先不要被它的名字唬住了,其实就是一个存储和快速读取大量键值对的工具.先思考一个问题, ...

  2. mysql数据库映射到内存_基于共享内存的数据库映射

    基于共享内存的数据库映射 概述 随着各类行业软件对性能追求越来越高,因此对数据库处理的速度提出了新的挑战.然而大部分复杂的业务处理往往依赖体量较大的关系数据(如:Oracle,Mysql,Postgr ...

  3. java内存映射缓存,java – 用于数据库实现的内存映射的MappedByteBuffer或直接ByteBuffer?...

    这看起来像一个长期的问题,因为所有的上下文.下面的小说里有两个问题.感谢您抽出时间阅读并提供帮助. 情况 我正在开展可扩展的数据存储实现,可以支持在32位或64位系统上处理数据文件,从几KB到TB或更 ...

  4. Redis 数据库入门教程

    From:http://www.jb51.net/article/56448.htm Redis 菜鸟教程:http://www.runoob.com/redis/redis-tutorial.htm ...

  5. 数据库入门理论知识介绍以及编译安装MySql

    数据库入门理论知识介绍以及编译安装MySql 作者:尹正杰 版权声明:原创作品,谢绝转载!否则将追究法律责任. 前言: 1.目前90%以上的公司面临的运维的瓶颈都在后端 最常见的2大瓶颈就是: 1&g ...

  6. 磁盘IO:缓存IO、直接IO、内存映射

    磁盘IO的几种访问方式如下: 缓存IO 缓存I/O又被称作标准I/O,大多数文件系统的默认I/O操作都是缓存I/O.在Linux的缓存I/O机制中,数据先从磁盘复制到内核空间的缓冲区,然后从内核空间缓 ...

  7. mysql nosql sqlite_自己做了一个轻量级的 NoSQL 数据库

    给大家介绍一个个人作品,叫 PoloDB,一个非常轻量级的 NoSQL 数据库,有着类似 MongoDB 的 API,主打几个特性: 轻量级 没有像 MySQL 那样的独立进程,它可以编译成静态库或者 ...

  8. .NET平台开源项目速览(3)小巧轻量级NoSQL文件数据库LiteDB

    今天给大家介绍一个不错的小巧轻量级的NoSQL文件数据库LiteDB.本博客在2013年也介绍过2款.NET平台的开源数据库: 1.[原创]开源.NET下的XML数据库介绍及入门 2.[原创]C#开源 ...

  9. mongodb内存映射原理

    内存映射 mongodb非常吃内存,为啥这么吃内存呢,mongodb使用的是内存映射存储引擎,即Memory Mapped Storage Engine,简称MMAP,MMAP可以把磁盘文件的一部分或 ...

  10. arraylist内存溢出_ArrayList使用内存映射文件

    arraylist内存溢出 介绍 内存中的计算由于负担得起的硬件而开始兴起,大多数数据保留在RAM中以满足延迟和吞吐量的目标,但是将数据保留在RAM中会增加垃圾收集器的开销,尤其是在您不预先分配内存的 ...

最新文章

  1. Linux 操作系统原理 — 零拷贝技术
  2. 【Flutter】Flutter Gallery 官方示例简介 ( 学习示例 | 邮件应用 | 零售应用 | 理财应用 | 旅行应用 | 新闻应用 | 自适应布局应用 )
  3. React as a UI Runtime(四、条件)
  4. HTK学习2:工具使用
  5. python运行是哪个键_python – 如何使用回车键调用按钮命令
  6. WINCE快捷方式详解
  7. oopc——0.概念及为何要学习oopc
  8. c++ 结构体初始化_单片机C语言 - 基于结构体的面向对象编程技巧
  9. python3 md5_Python3.2 --md5
  10. C++--第24课 - 专题四经典问题解析
  11. 补一天三层的东西,ACL
  12. 编程语言中,取余和取模的区别到底是什么?
  13. PMP课程笔记:第7章 项目成本管理
  14. 使用html查看dicom,使用LEADTOOLS HTML5 Medical Viewer从任何地方查看DICOM图像教程
  15. access简述报表的功能_access中报表的作用
  16. CANopen基本原理及其应用(二)——对象字典和通讯机制
  17. GitHub爆火 金九银十巨作:拼多多/蚂蚁/百度面经分享
  18. 关于iPad作为Win10系统拓展屏的心得
  19. 计算机一级怎么截图保存到桌面,怎么截屏电脑桌面
  20. v-model的用法与解析

热门文章

  1. 单总线CPU微程序条件判别测试逻辑
  2. 南京信息工程大学eduroam使用方法
  3. Matlab PlotPub绘图工具箱
  4. 如何用Directshow采集摄像头图像
  5. DirectShow 开启摄像头
  6. Flash CS 6绘图技巧之锁定填充
  7. js读取剪切板html,JS获取剪贴板的内容
  8. 量子计算机采用量子力学原理,量子计算机的工作是不是就是根据量子力学原理造的?...
  9. VARCHART XGantt_v5.1用户手册:如何提供数据(.NET版)
  10. 考试日复习【字符串处理函数】