使用Llama.cpp在本地高效运行经过微调的LLM

2023年10月09日 由 alex 发表 1079 0

简介


最近,将LLM(Language Model)运行在计算机的CPU上引起了很大的关注,有许多工具试图使此过程更加简单和快速。本文重点介绍了Llama.cpp,展示了运行LLaMa 27b并超过我们所熟悉的深度学习模型的传统运行时基准的功能。Llama.cpp是各种LLM架构模型的推理实现,纯粹用C/C++编写,因此具有非常高的性能。


第一步:选择你的模型


Llama.cpp希望以“gguf”格式保存LLM模型。


有时候你可能需要将你的PyTorch模型权重转换为gguf格式。我们将逐步指导你完成这个过程!


安装 


首先,让我们获取llama.cpp并进行设置:


git clone llama.cpp
cd llama.cpp
MAKE # If you got CPU 
MAKE CUBLAS=1 # If you got GPU


接下来,我们应该从huggingface下载任何基于llama.cpp支持的模型架构之一的原始权重。


下载模型如下:


pip install transformers datasets sentencepiece
huggingface-cli download Universal-NER/UniNER-7B-type --local-dir models


检查模型文件夹以确保所有内容已下载。然后,运行llama.cpp转换脚本。


python convert.py ./modelspy ./models


脚本将原始的.pth文件转换成.gguf格式。你会看到一个名为ggml-model-f32.gguf的文件,其大小为27G。


1


gguf格式是最近才新出来的,于8月23日发布。它用于加载权重并运行cpp代码。


这是一个必要的步骤,以便能够后续将模型加载到llama.cpp中。


量化


深度神经网络的量化是将完整精度的权重(32位浮点数)转换为较小的近似表示,如4位/8位等等的过程。


为什么这很重要?


1. 小型模型使用的VRAM较少,对于你的GPU来说更容易。


2. 它们更轻巧。


3. 运行速度更快。


下面是使用llama.cpp缩小模型的不同方法的简要介绍:


2


选择较小的位点可以使模型运行更快,但可能会稍微牺牲一些准确性。我们将使用q4_1,它在速度和准确性之间取得了良好的平衡。


./quantize models/ggml-model-f32.gguf models/quantized_q4_1.gguf q4_1gguf models/quantized_q4_1.gguf q4_1


每个权重层应该减小约7倍,所以最终大小应该是原始大小的1/7!


3


让我们比较原始模型和量化模型的大小。


ls ./models


原始重量:26.9克|缩小后:4.2克 


4


你的模型现在变得更小、更快了。


运行模型


你有两种主要的方式来运行你的cpp模型:


1. CLI推断:模型加载,运行提示,并一次性卸载。适用于单次运行。


2. 服务器推断:模型加载到内存中并启动服务器。只要服务器在运行,模型就会一直保持加载状态。


要运行服务器:


./server -m ./models/quantized_q4_1.gguf -c 1024


日志将告诉你服务器正在运行!


5


做出预测


通过API调用,我们获取预测信息。


url = f"http://localhost:8000/completion""http://localhost:8000/completion"
prompt = "<prompt_placeholder>"
req_json = {
    "stream": False,
    "n_predict": 400,
    "temperature": 0,
    "stop": [
        "</s>",
    ],
    "repeat_last_n": 256,
    "repeat_penalty": 1,
    "top_k": 20,
    "top_p": 0.75,
    "tfs_z": 1,
    "typical_p": 1,
    "presence_penalty": 0,
    "frequency_penalty": 0,
    "mirostat": 0,
    "mirostat_tau": 5,
    "mirostat_eta": 0.1,
    "grammar": "",
    "n_probs": 0,
    "prompt": prompt
}
res = requests.post(url, json=req_json)
result = res.json()["content"]


表现如何?


我们通过每秒能处理多少个令牌(文本片段)来衡量性能。每次运行都涉及以下内容:


1. 提示评估 - 处理提示令牌所需的时间。


2. 生成 - 生成新令牌所需的时间。


3. 采样 - 采样不同可能性所需的时间。


运行 q4_1 缩小模型给出的结果如下:


提示:"一个虚拟助手根据提供的文本回答用户的问题。用户:“除了儿童哮喘外,我没有值得一提的病史。”助手:我已阅读完这段文本。</s>用户:文本中描述了哪些医疗史?助手:"


输出:["儿童哮喘"]


结果 


6


处理该请求所花费的总时间为804毫秒,少于1秒!


记住,在LLM的世界里,关键是能够每秒处理多少个标记,越高越好!


文章来源:https://medium.com/vendi-ai/efficiently-run-your-fine-tuned-llm-locally-using-llama-cpp-66e2a7c51300
欢迎关注ATYUN官方公众号
商务合作及内容投稿请联系邮箱:bd@atyun.com
评论 登录
热门职位
Maluuba
20000~40000/月
Cisco
25000~30000/月 深圳市
PilotAILabs
30000~60000/年 深圳市
写评论取消
回复取消