MapDB 教程

MapDB 安装 & 入门

MapDB 的二进制文件托管在 Maven 中央仓库中。

安装 MapDB 非常简单,只需要在你的 Maven 项目的 pom.xml 中添加如下依赖即可:

<!-- Source: https://mvnrepository.com/artifact/org.mapdb/mapdb -->
<dependency>
  <groupId>org.mapdb</groupId>
  <artifactId>mapdb</artifactId>
  <version>3.0.8</version>
</dependency>

注意,上面使用 3.0.8 版本,最新版本可以到 https://mvnrepository.com 网站查询。

你也可以直接从 Maven Central 下载 MapDB 的 jar 文件。在这种情况下,MapDB 依赖于 Eclipse Collections、Guava、Kotlin 库以及其他一些库,也需要自己下载。

点击查看每个 MapDB 版本的完整依赖列表

Hello World

以下是一个简单的示例。

它会打开内存中的 HashMap,使用堆外存储,且不受垃圾回收的限制。

完整代码如下:

package com.hxstrive.mapdb;

import org.mapdb.DB;
import org.mapdb.DBMaker;
import org.mapdb.HTreeMap;
import org.mapdb.Serializer;
import java.util.concurrent.ConcurrentMap;

/**
 * MapDB 极简 Hello World 示例(内存模式)
 * 功能:演示 MapDB 内存数据库的创建、数据新增、数据读取核心操作
 * 特点:内存模式下数据仅存在于运行时,程序退出后数据丢失,无持久化文件
 */
public class MapDbHello {

    public static void main(String[] args) {
        // 1. 创建内存数据库实例,使用 try-with-resources 语法自动关闭资源
        //    DBMaker.memoryDB():创建纯内存数据库(非持久化)
        //    make():生成 DB 实例,是 MapDB 数据库操作的核心入口
        //    try-with-resources 特性:代码块执行完毕后自动调用 DB.close(),避免内存泄漏
        try (DB memoryDB = DBMaker.memoryDB().make()) {

            // 2. 创建/打开一个名为 "map" 的哈希映射表(HTreeMap)
            //    hashMap("map"):指定映射表的名称为 "map",用于区分不同的数据集
            //    Serializer.STRING:指定键和值的序列化器为字符串类型
            //    createOrOpen():如果 "map" 不存在则创建,存在则直接打开
            ConcurrentMap<String, String> map = memoryDB
                    .hashMap("map", Serializer.STRING, Serializer.STRING)
                    .createOrOpen();

            // 3. 向映射表中添加键值对数据
            //    put(key, value):类似 Java HashMap 的新增/修改操作
            //    此处添加键为 "content",值为 "Hello MapDB" 的数据
            map.put("content", "Hello MapDB");

            // 4. 从映射表中读取指定键的数据
            //    get(key):根据键获取对应的值,键不存在时返回 null
            String value = map.get("content");
            System.out.println("value=" + value);

        } catch (Exception e) {
            e.printStackTrace();
        }
    }

}

运行示例,输出如下:

value=Hello MapDB

Process finished with exit code 0

HashMap(以及其他集合)也可以存储在文件中。在这种情况下,内容可以在JVM重启之间保留。

但是必须调用 DB.close() 方法关闭资源以防止文件数据损坏。另一种选择是通过预写日志启用事务。

示例:将数据持久化到 file.db

package com.hxstrive.mapdb;

import org.mapdb.DB;
import org.mapdb.DBMaker;
import org.mapdb.Serializer;
import java.util.concurrent.ConcurrentMap;

/**
 * MapDB持久化存储示例
 * MapDB是一个嵌入式的键值存储数据库,支持内存和磁盘持久化
 * 本示例演示如何使用MapDB将数据持久化到文件中
 */
public class MapDbPersistent {

    public static void main(String[] args) {
        // 使用try-with-resources语法,自动关闭数据库资源,避免资源泄漏
        // 1. 创建并配置MapDB数据库实例
        // fileDB("file.db"): 指定数据库文件名为file.db,数据会持久化到该文件
        // make(): 构建数据库实例
        try (DB memoryDB = DBMaker.fileDB("file.db").make()) {
            // 2. 创建或打开一个HashMap结构
            // hashMap("map"): 指定map的名称为"map",作为唯一标识
            // Serializer.STRING: 指定键和值的序列化器为字符串序列化器
            // createOrOpen(): 如果该map不存在则创建,存在则打开
            ConcurrentMap<String, String> map = memoryDB
                    .hashMap("map", Serializer.STRING, Serializer.STRING)
                    .createOrOpen();

            // 3. 向map中存入键值对数据
            map.put("content", "Hello MapDB");

            // 4. 从map中读取指定键的值
            String value = map.get("content");
            System.out.println("value=" + value);

        } catch (Exception e) {
            e.printStackTrace();
        }
    }

}

运行示例,查看项目目录,会多一个 file.db 文件,如下图:

默认情况下,MapDB 使用通用序列化,这种序列化可以对任何数据类型进行序列化。

但是我们可以手动指定专用的序列化起,使用专用序列化器会更快,且内存效率更高。此外,我们可以在 64 位操作系统上启用更快的内存映射文件:

// fileMmapEnable() 用于开启内存映射文件
DB db = DBMaker.fileDB("file.db").fileMmapEnable().make();
ConcurrentMap<String,Long> map = db
        // 手动为键/值指定专用的序列化器
        .hashMap("map", Serializer.STRING, Serializer.STRING)
        .createOrOpen();

// 写入数据
map.put("content", "Hello MapDB");

// 关闭数据库,可以利用 try-with-resources 自动关闭
db.close();

注意:DB 实现了 java.io.Closeable 接口。

快速提示

  • 内存映射文件速度快得多,为了获得更好的性能,应在 64 位系统上启用它。

  • MapDB 有用于快速批量导入集合的 Pump,它比 Map.put() 快得多。

  • 事务会带来性能开销,但如果没有事务,存储在未被正确关闭的情况下会损坏。

  • 存储在 MapDB 中的数据(键和值)应该是不可变的。MapDB 会在后台对对象进行序列化。

  • MapDB 有时需要压缩。运行 DB.compact() 或者查看后台压缩选项。

更多关于 MapDB 的知识,请继续学习后续教程🚀

  

说说我的看法
全部评论(
没有评论
关于
本网站专注于 Java、数据库(MySQL、Oracle)、Linux、软件架构及大数据等多领域技术知识分享。涵盖丰富的原创与精选技术文章,助力技术传播与交流。无论是技术新手渴望入门,还是资深开发者寻求进阶,这里都能为您提供深度见解与实用经验,让复杂编码变得轻松易懂,携手共赴技术提升新高度。如有侵权,请来信告知:hxstrive@outlook.com
其他应用
公众号