一个轻量级、单头文件的 C++11 Jinja2 模板引擎,专为 LLM Chat 模板设计。
它专注于支持现代大语言模型 (如 Llama 3, Qwen 2.5/3, DeepSeek 等) 所需的 Jinja2 语法子集,使得在 C++ 环境中进行推理集成变得无缝且高效。
- C++11 兼容:确保在旧版编译器和嵌入式系统上的最大兼容性。
- 灵活的 JSON 后端:通过统一的
ujson桥接层支持nlohmann/json(默认) 和RapidJSON。 - 轻量级:依赖极少,所有必要头文件均已包含在
third_party/目录下。 - 专注 LLM:原生支持
messages,tools,add_generation_prompt以及特殊 token 的处理。 - 统一上下文:使用
jinja::json(即ujson::json的别名) 进行无缝的上下文管理。 - 自定义函数:支持轻松注入 C++ 函数 (如
strftime_now) 到模板中。 - 健壮性:通过 390+ 条测试用例验证,与官方 Python
transformers输出进行对齐。
已基于以下模型的真实模板进行测试验证:
- Qwen 2.5 / 3 (Coder, Math, VL, Omni, Instruct, Thinking, QwQ)
- DeepSeek (V3, R1)
- Llama 3 / 3.1 / 3.2 (Instruct & Vision)
- Mistral
- Gemma
- SmolLM
- Phi
- 更多...
- CMake 3.10+
- 支持 C++11 的编译器 (GCC, Clang, MSVC)
mkdir build
cd build
cmake ..
make为了获得更好的性能,可以切换到 RapidJSON 后端:
cmake .. -DUJSON_USE_RAPIDJSON=ON注:请确保 third_party/rapidjson 存在。
本项目包含一个基于真实模型模板的全面测试套件。
./test_main#include "jinja.hpp"
#include <iostream>
int main() {
std::string template_str = "Hello {{ name }}!";
jinja::Template tpl(template_str);
jinja::json context;
context["name"] = "World";
std::string result = tpl.render(context);
std::cout << result << std::endl; // 输出: Hello World!
return 0;
}#include "jinja.hpp"
// 加载 tokenizer_config.json 中的 "chat_template" 字符串
std::string chat_template_str = "...";
jinja::Template tpl(chat_template_str);
jinja::json messages = jinja::json::array({
{{"role", "user"}, {"content", "你好!"}}
});
// 应用模板
std::string prompt = tpl.apply_chat_template(
messages,
true, // add_generation_prompt
jinja::json::array() // tools
);你可以注册自定义 C++ 函数,供模板内部调用。
tpl.add_function("strftime_now", [](const std::vector<jinja::json>& args) {
// 返回当前时间字符串
return "2025-12-16";
});关于具体的实现细节,请参阅 doc/implementation_details_CN.md。
Apache License 2.0。 详见 LICENSE 文件。