从加载到对话:使用 Llama-cpp-python 本地运行量化 LLM 大模型(GGUF)

(无需显卡)使用 Llama-cpp-python 在本地加载具有 70 亿参数的 LLM 大语言模型,通过这篇文章你将学会用代码创建属于自己的 GPT。
建议阅读完 19a 的「前言」和「模型下载」部分后再进行本文的阅读。

代码文件下载:Llama-cpp-python | 🎡 AI Chat 脚本

在线链接:Kaggle - b | Colab - b

Llama-cpp-python

环境配置

为了确保后续的 “offload”(卸载到 GPU)功能正常工作,需要进行一些额外的配置。

首先,找到 CUDA 的安装路径(你需要确保已经安装了 CUDA):

find /usr/local -name "cuda" -exec readlink -f {} \;

参数解释

  • -name "cuda":在 /usr/local 目录下搜索名为 “cuda” 的文件或目录。
  • -exec readlink -f {} \;:对找到的每个文件或目录执行 readlink -f,获取其完整的绝对路径。

假设输出如下:

/usr/local/cuda-12.1
...

复制这个路径,设置 CUDA_HOME 环境变量:

export CUDA_HOME=/usr/local/cuda-12.1

接下来,安装 llama-cpp-python

CMAKE_ARGS="-DGGML_CUDA=on \
            -DCUDA_PATH=${CUDA_HOME} \
            -DCUDAToolkit_ROOT=${CUDA_HOME} \
            -DCUDAToolkit_INCLUDE_DIR=${CUDA_HOME} \
            -DCUDAToolkit_LIBRARY_DIR=${CUDA_HOME}/lib64 \
            -DCMAKE_CUDA_COMPILER=/usr/local/cuda/bin/nvcc" \
FORCE_CMAKE=1 \
pip install --upgrade --force-reinstall llama-cpp-python --no-cache-dir --verbose

[!note]

如果仅在 CPU 上运行,可以直接使用 pip install llama-cpp-python 进行安装。

否则,请确保系统已安装 CUDA,可以通过 nvcc --version 检查。

GGUF

bartowski/Mistral-7B-Instruct-v0.3-GGUF 为例进行演示。你将在模型界面查看到以下信息:

image-20241007093704658

可以看到 4-bit 量化有 IQ4_XSQ4_K_SIQ4_NLQ4_K_M 四种,出于性能的考虑,我们将选择 Q4_K_M 进行加载。

文件名量化类型文件大小描述
Mistral-7B-Instruct-v0.3-Q4_K_M.ggufQ4_K_M4.37GB质量较好,权重每位约占 4.83 比特,推荐使用
Mistral-7B-Instruct-v0.3-Q4_K_S.ggufQ4_K_S4.14GB略低于 Q4_K_M 的质量,但节省更多空间,推荐使用
Mistral-7B-Instruct-v0.3-IQ4_NL.ggufIQ4_NL4.13GB质量不错,体积略小于 Q4_K_S,性能相近,推荐使用
Mistral-7B-Instruct-v0.3-IQ4_XS.ggufIQ4_XS3.91GB质量不错,体积小于 Q4_K_S,性能相近,推荐使用

[!NOTE]

Q:这些量化类型到底是什么?
A:拓展阅读:《d. 如何加载 GGUF 模型(分片/Shared/Split/00001-of-0000…的解决方法)》,其中还会以 Qwen2.5-7B 为例讲述分片模型的加载方式。

安装库

pip install gguf

导入库

from llama_cpp import Llama

下面介绍两种导入模型的方法,实际执行时在本地导入和自动下载中选择一种即可。

本地导入模型

根据模型路径导入模型,注意,文件位于 <model_name> 文件夹下,以当前下载的文件为例:

# 指定本地模型的路径
model_path = "./Mistral-7B-Instruct-v0.3-GGUF/Mistral-7B-Instruct-v0.3-Q4_K_M.gguf"

# 加载模型
llm = Llama(
    model_path=model_path,
    #n_gpu_layers=-1,  # 取消注释使用 GPU 加速
    #verbose=False,  # 取消注释禁用详细日志输出
)

自动下载并导入模型

对于 llama-cpp-python,入乡随俗使用 repo_id 变量名,但本质是和之前一致的,filename 可以使用通配符,比如 "*Q4_K_M.gguf"

# 指定仓库的名称和文件名
repo_id = "bartowski/Mistral-7B-Instruct-v0.3-GGUF"
filename = "Mistral-7B-Instruct-v0.3-Q4_K_M.gguf"
#filename = "*Q4_K_M.gguf"  # 使用通配符也是可以的

# 下载并加载模型
llm = Llama.from_pretrained(
    repo_id=repo_id,
    filename=filename,
    #n_gpu_layers=-1,  # 取消注释使用 GPU 加速
    #verbose=False,  # 取消注释禁用详细日志输出
)

[!tip]

二者的函数区别在于 Llama()Llama.from_pretrained()

推理测试

使用以下代码进行简单的推理测试:

# 输入文本
input_text = "Hello, World!"

# 生成输出
output = llm(input_text, max_tokens=50)

# 打印生成的文本
print(output['choices'][0]['text'])

输出

Llama.generate: 4 prefix-match hit, remaining 1 prompt tokens to eval
llama_perf_context_print:        load time =      28.32 ms
llama_perf_context_print: prompt eval time =       0.00 ms /     1 tokens (    0.00 ms per token,      inf tokens per second)
llama_perf_context_print:        eval time =       0.00 ms /   100 runs   (    0.00 ms per token,      inf tokens per second)
llama_perf_context_print:       total time =    1563.56 ms /   101 tokens


Welcome to the latest post on my blog. Today, we will discuss an interesting topic: “How to create a website using JavaScript, HTML, and CSS“. This article is for those who are new to web development or want to learn the basics of creating a website using these technologies. Let’s dive in!

# Prerequisites

Before we start, I would like to mention that I am assuming that you have some basic knowledge of HTML, CSS,

每次生成都会打印一些时间方面的信息,设置 Llama() 的参数 verbose 为 False 可以禁止这个行为。

卸载到 GPU 加速推理

当前的模型默认被部署在 CPU 上,如果你的电脑拥有显卡且大于 5G 显存,那么可以增加 n_gpu_layers 参数将部分计算卸载(offload)到 GPU,以加速推理。修改加载模型的代码如下:

# 本地加载并卸载到 GPU
llm = Llama(
    model_path=model_path,
    n_gpu_layers=-1  # 将所有层卸载到 GPU
    verbose=False,  # 禁用详细日志输出
)

# 或者,自动下载并卸载到 GPU
llm = Llama.from_pretrained(
    repo_id=repo_id,
    filename=filename,
    n_gpu_layers=-1  # 将所有层卸载到 GPU
    verbose=False,  # 禁用详细日志输出
)

如果你的显卡不足 5G,可以设置卸载的具体层数,例如 n_gpu_layers=20,根据你的显存大小调整该参数。

P.S. 不卸载层是允许的,使用 CPU 一样可以进行推理,简单参考下面的表格:

设备tokens/sms/tokens/100 tokens
CPU11.4887.088.71
GPU66.8514.961.50

注:tokens/s 为每秒生成的 Token 数量,ms/token 为生成每个 Token 所需的毫秒数,s/100 tokens 为生成 100 个 Token 所需的秒数。

流式输出

Llama-cpp-python 的流式输出只需要在 create_chat_completion() 中传递参数 stream=True 就可以开启,以本地模型导入为例:

prompt = "人工智能的未来发展方向是什么?"

output = llm.create_chat_completion(
    messages=[{
        "role": "user",
        "content": prompt
    }],
    max_tokens=200,
    stream=True
)

for chunk in output:
    delta = chunk['choices'][0]['delta']
    if 'role' in delta:
        print(delta['role'], end=': ', flush=True)
    elif 'content' in delta:
        print(delta['content'], end='', flush=True)

输出

流式输出 llama-cpp-python

代码解释

  • for chunk in output::遍历模型生成的每一个数据块(chunk)。
    • delta = chunk['choices'][0]['delta']

      • 每个chunk包含一个choices列表,这里只取第一个选择(choices[0])。
      • delta包含了当前数据块中的增量信息,可能是角色(role)信息或内容(content)信息。
    • if 'role' in delta:

      • 如果delta中包含'role'键,说明这是角色信息(例如 “assistant”)。
      • print(delta['role'], end=': '):打印角色名,并以冒号和空格结尾,例如“assistant: ”,这是自定义行为,当然也可以 pass 掉。
    • elif 'content' in delta:

      • 如果delta中包含'content'键,说明这是实际的回答内容。
        • print(delta['content'], end=''):打印内容,不换行,以便逐步显示生成的回答,注意,在这里参数 end='' 是正确打印所必须的。

[!note]

查看 output 的构造

from itertools import islice

prompt = "人工智能的未来发展方向是什么?"

output = llm.create_chat_completion(
    messages=[{
        "role": "user",
        "content": prompt
    }],
    max_tokens=200,
    stream=True
)

print(type(output))

# 将生成器转换为列表
output_list = list(itertools.islice(output, 3))

# 获取前 3 个条目
output_list[:3]

输出(只需要查看其中的 delta):

<class 'generator'>
[{'id': 'chatcmpl-848b2e9b-7d70-4a7b-99aa-74b8206721db',
'model': './Mistral-7B-Instruct-v0.3-GGUF/Mistral-7B-Instruct-v0.3-Q4_K_M.gguf',
'created': 1728562647,
'object': 'chat.completion.chunk',
'choices': [{'index': 0,
 'delta': {'role': 'assistant'},
 'logprobs': None,
 'finish_reason': None}]},
{'id': 'chatcmpl-848b2e9b-7d70-4a7b-99aa-74b8206721db',
'model': './Mistral-7B-Instruct-v0.3-GGUF/Mistral-7B-Instruct-v0.3-Q4_K_M.gguf',
'created': 1728562647,
'object': 'chat.completion.chunk',
'choices': [{'index': 0,
 'delta': {'content': ' '},
 'logprobs': None,
 'finish_reason': None}]},
{'id': 'chatcmpl-848b2e9b-7d70-4a7b-99aa-74b8206721db',
'model': './Mistral-7B-Instruct-v0.3-GGUF/Mistral-7B-Instruct-v0.3-Q4_K_M.gguf',
'created': 1728562647,
'object': 'chat.completion.chunk',
'choices': [{'index': 0,
 'delta': {'content': '人'},
 'logprobs': None,
 'finish_reason': None}]}]

将刚刚对于流式输出的处理抽象为函数便于后续调用:

def handle_stream_output(output):
    """
    处理流式输出,将生成的内容逐步打印出来。
    
    参数:
        output: 生成器对象,来自 create_chat_completion 的流式输出
    """
    for chunk in output:
        delta = chunk['choices'][0]['delta']
        if 'role' in delta:
            print(f"{delta['role']}: ", end='', flush=True)
        elif 'content' in delta:
            print(delta['content'], end='', flush=True)
            
# 使用示例
prompt = "人工智能的未来发展方向是什么?"

output = llm.create_chat_completion(
    messages=[{
        "role": "user",
        "content": prompt
    }],
    max_tokens=200,
    stream=True
)

handle_stream_output(output)

函数解释

  • handle_stream_output
    • 接收一个生成器对象 output,遍历每个数据块 chunk
    • 从每个 chunk 中提取 delta 信息。
    • 根据 delta 中的键值,分别处理 rolecontent 信息。
    • 使用 flush=True 确保内容实时打印。

多轮对话

让我们自定义一个交互的对话类(需要注意到 handle_stream_output() 有所修改)。

from llama_cpp import Llama

def handle_stream_output(output):
    """
    处理流式输出,将生成的内容逐步打印出来,并收集完整的回复。

    参数:
        output: 生成器对象,来自 create_chat_completion 的流式输出

    返回:
        response: 完整的回复文本
    """
    response = ""
    for chunk in output:
        delta = chunk['choices'][0]['delta']
        if 'role' in delta:
            print(f"{delta['role']}: ", end='', flush=True)
        elif 'content' in delta:
            content = delta['content']
            print(content, end='', flush=True)
            response += content
    return response

class ChatSession:
    def __init__(self, llm):
        self.llm = llm
        self.messages = []

    def add_message(self, role, content):
        """
        添加一条消息到会话中。

        参数:
            role: 消息角色,通常为 'user' 或 'assistant'
            content: 消息内容
        """
        self.messages.append({"role": role, "content": content})

    def get_response_stream(self, user_input):
        """
        获取模型对用户输入的响应(流式输出)。

        参数:
            user_input: 用户输入的文本

        返回:
            response: 完整的回复文本
        """
        self.add_message("user", user_input)
        
        try:
            output = self.llm.create_chat_completion(
                messages=self.messages,
                stream=True  # 开启流式输出
            )
            
            response = handle_stream_output(output)  # 同时打印和收集回复
            
            self.add_message("assistant", response.strip())
            return response.strip()
        except Exception as e:
            print(f"\n发生错误: {e}")
            return ""

# 初始化模型(假设使用本地路径)
model_path = "./Mistral-7B-Instruct-v0.3-GGUF/Mistral-7B-Instruct-v0.3-Q4_K_M.gguf"
llm = Llama(
    model_path=model_path,
    n_gpu_layers=-1,  # 根据需要卸载到 GPU
    verbose=False,    # 禁用详细日志输出
)

# 创建会话实例
chat = ChatSession(llm)
        
# 开始对话
while True:
    prompt = input("User: ")
    # 退出对话条件(当然,你也可以直接终止代码块)
    if prompt.lower() in ["exit", "quit", "bye"]:
        print("Goodbye!")
        break
    chat.get_response_stream(prompt)
    print()  # 换行以便下一次输入,这是因为之前的 print 都设置了 end=''

输出

User:  如果你是大模型面试官,你会怎么出面试题
assistant:  以下是一些可能的大模型面试题:

1. 解释什么是深度学习和卷积神经网络,以及它们的应用场景。
2. 描述你对数据预处理和特征工程的了解,并提供一个实际使用例子。
3. 如何选择合适的模型、优化器和损失函数,以及如何评估模型性能?
4. 解释你对TensorFlow和PyTorch的了解,并提供一个使用它们的实际例子。
5. 如何处理不平衡数据集,以及你对样本平衡和数据增强方法的了解。
6. 如何使用Transfer Learning来提高模型性能,并提供一个实际例子。
7. 如何使用文本生成模型(如Seq2Seq模型)来进行机器翻译,文本摘要和情感分析?
8. 如何使用对象检测模型(如Faster R-CNN和YOLO)来进行目标检测?
9. 如何使用自编码器来进行数据压缩和特征学习?
10. 如何使用喂给网络(Feeding Networks)和Generative Adversarial Networks(GANs)来生成图像和文本?
11. 如何使用时序数据模型(如ARIMA和LSTM)来进行预测?
12. 如何使用回归树和随机森林来进行预测和分类?
13. 描述你对超参数调优的了解,包括网络架构、学习率和批大小等方面。
14. 如何使用K-means和朴素贝叶斯等聚类和分类方法?
15. 描述你对凸优化和
User:  对于第十个问题能否给我答案

发生错误: Requested tokens (530) exceed context window of 512

可以看到报错超过了上下文窗口的长度,让我们增加它:

llm = Llama(
    model_path=model_path,
    n_gpu_layers=-1,  # 根据需要卸载到 GPU
    n_ctx=4096,       # 设置上下文窗口大小
    verbose=False,    # 禁用详细日志输出
)

此时模型输出正常:

User:  如果你是大模型面试官,你会怎么出面试题
assistant:  以下是一些可能的大模型面试题:

1. 解释什么是深度学习和卷积神经网络,以及它们的应用场景。
2. 描述你对数据预处理和特征工程的了解,并提供一个实际使用例子。
3. 如何选择合适的模型、优化器和损失函数,以及如何评估模型性能?
4. 解释你对TensorFlow和PyTorch的了解,并提供一个使用它们的实际例子。
5. 如何处理不平衡数据集,以及你对样本平衡和数据增强方法的了解。
6. 如何使用Transfer Learning来提高模型性能,并提供一个实际例子。
7. 如何使用文本生成模型(如Seq2Seq模型)来进行机器翻译,文本摘要和情感分析?
8. 如何使用对象检测模型(如Faster R-CNN和YOLO)来进行目标检测?
9. 如何使用自编码器来进行数据压缩和特征学习?
10. 如何使用喂给网络(Feeding Networks)和Generative Adversarial Networks(GANs)来生成图像和文本?
11. 如何使用时序数据模型(如ARIMA和LSTM)来进行预测?
12. 如何使用回归树和随机森林来进行预测和分类?
13. 描述你对超参数调优的了解,包括网络架构、学习率和批大小等方面。
14. 如何使用K-means和朴素贝叶斯等聚类和分类方法?
15. 描述你对凸优化和随机 Forests等算法的了解。
User:  对于第十个问题能否给我答案
assistant:  给定一个生成图像和文本的问题,一种方法是使用Generative Adversarial Networks(GANs)。

GANs是一种深度学习模型,由两个子网络组成:生成器和判别器。生成器生成一组随机噪声并根据该噪声生成新的数据,而判别器试图区分生成的数据和真实数据。这两个子网络通过最小化一个对抗性损失函数来互相学习。

在生成图像方面,常用的GAN模型包括DCGAN(Deep Convolutional GAN)、CGAN(Conditional GAN)和WGAN(Wasserstein GAN)等。DCGAN使用 convolutional neural network 作为生成器,对于生成图像来说,DCGAN可以生成高质量的图像,但是它可能会生成一些不太可靠的图像,因为它是一种无条件生成器。

CGAN是DCGAN的一种扩展,它引入了条件信息,允许生成器根据特定条件(如类别标签)生成图像。WGAN是DCGAN的一种改进版本,它使用 Wasserstein 距离来替换了原来的对抗性损失函数,从而使得模型更加稳定。

在生成文本方面,常用的GAN模型包括SeqGAN(Sequence Generative Adversarial Nets)和StackGAN(Stack Generative Adversarial Networks)。SeqGAN通过使用RNNs(Recurrent Neural Networks)生成一系列单词来生成文本。StackGAN使用多个堆叠的GAN子网络来生成复杂的文本。

总之,GANs是一种强大的生成模型,可以生成高质量的图像和文本,但是它们也有一些问题,例如生成的数据可能存在模式缺陷,并且训练过程可能会收敛很慢。

至此,篇章告一段落 : )。

请注意,这只是一个简短的章节,其中还有许多知识尚未涉及,比如 Transformers 中的 Pipeline,对 Tokenizer 的更深入了解,以及 RAG 的应用等。由于内容过多,文章跳过了一些细节,预计闲暇时增设章节单独进行讲解。

用 🎡 脚本感受 AI 对话(可选)

这是可选的行为,脚本的代码处理逻辑与文章对应。

克隆仓库

# 如果已经克隆仓库的话跳过这行
git clone https://github.com/Hoper-J/AI-Guide-and-Demos-zh_CN

执行脚本

  1. 切换到 CodePlayground 文件夹:

    cd AI-Guide-and-Demos-zh_CN/CodePlayground
    
  2. 开始对话:

    # 使用方法:python chat.py <model_path> [可选参数],替换为你想用的 <model_path>
    # 本地加载
    python chat.py ../Demos/Mistral-7B-Instruct-v0.3-GGUF/Mistral-7B-Instruct-v0.3-Q4_K_M.gguf
    
    # 远程加载
    python chat.py bartowski/Mistral-7B-Instruct-v0.3-GGUF/Mistral-7B-Instruct-v0.3-Q4_K_M.gguf --remote
    
    # 远程加载(通配符版)
    python chat.py 'bartowski/Mistral-7B-Instruct-v0.3-GGUF/*Q4_K_M.gguf' --remote
    

加载和保存历史对话

使用 -i 参数指定文件加载,-o 参数进行保存,或者 -io 参数指明加载和保存的文件路径相同:

python chat.py <model_path> -io history

注意,Ctrl + C 将直接终止对话,只有使用 ‘exit’、‘quit’ 或 ‘bye’ 结束对话,或者使用 Ctrl + D (EOF) 退出时才会保存对话。

暂时仅支持与拥有 tokenizer.chat_template 属性的模型对话。

参考链接

<think>好的,我现在需要帮助用户在Debian 12.9系统上,使用4G显存的显卡,通过sglang部署一个GGUF量化模型。首先,我得了解用户的具体需求和当前的环境情况。 用户提到的是Debian 12.9,这是一个稳定的Linux发行版,所以需要确保所有的依赖项都兼容这个版本。接下来,显存只有4G,这意味着模型的大小必须足够小,或者在量化时选择足够低的位数(比如4位或5位)来减少显存占用。GGUFllama.cpp引入的模型格式,支持量化,所以需要确认sglang是否支持GGUF格式的模型加载。 首先,我应该检查sglang的官方文档,看看它是否支持GGUF模型。如果支持,那么步骤可能包括安装sglang,下载GGUF模型,然后编写代码或使用命令行工具来部署。如果不支持,可能需要通过llama.cpp作为后端,或者sglang是否有集成llama.cpp的方法。 另外,用户的显存较小,可能需要使用CPU卸载功能,即部分计算在CPU上进行,以减少显存压力。llama.cpp支持这种功能,但需要确认sglang是否也支持。或者,用户可能需要调整模型的上下文长度、批次大小等参数来适应显存限制。 安装步骤方面,用户需要安装sglang,可能需要Python环境,因为很多这类库是通过Python接口使用的。需要确保Debian系统安装了Python 3.x,pip,以及可能的CUDA驱动(如果使用NVIDIA显卡)。不过,4G显存可能比较紧张,尤其是对于较大的模型,所以必须选择合适的模型大小。 GGUF模型可以从Hugging Face等平台获取,比如TheBloke发布的模型,通常会有不同量化的版本。用户需要选择适合4G显存的模型,比如Llama-2-7B的4位量化版本,或者更小的模型如Phi-2的GGUF版本。 接下来,安装sglang可能需要通过pip安装,但需要查看是否有预编译的版本或是否需要从源码编译。可能的依赖项包括PyTorch、transformers库等。如果sglang依赖llama.cpp,那么还需要安装llama.cppPython绑定,比如llama-cpp-python。 在部署过程中,用户可能需要编写一个脚本,使用sglang的API加载模型,并设置适当的参数,如n_ctx(上下文长度)、n_gpu_layers(在GPU上运行的层数)等。对于显存有限的系统,可能需要将大部分层卸载到CPU,只保留少量层在GPU上,这需要平衡速度和内存使用。 可能的挑战包括:sglang是否与GGUF兼容,安装过程中的依赖冲突,显存不足导致模型无法加载。需要指导用户如何解决这些问题,比如选择更小的模型,调整卸载层数,或者增加交换空间(虽然会影响性能)。 总结步骤大致如下: 1. 确认系统环境:安装必要的驱动和依赖。 2. 安装sglang和相关库。 3. 下载合适的GGUF模型。 4. 编写或使用sglang的脚本加载模型,配置参数优化显存使用。 5. 测试运行,处理可能出现的错误,如显存不足。 需要提醒用户注意模型选择,4G显存可能只能运行7B以下的4位量化模型,并可能需要减少上下文长度或批次大小。此外,如果sglang本身不支持GGUF,可能需要通过llama.cpp的API来加载模型,并与sglang结合使用,或者寻找其他支持GGUF部署工具。</think>在 Debian 12.9 系统上使用 4G 显存的 GPU 部署 GGUF 量化模型,结合 `sglang`(一个高效的推理框架),以下是分步指南: --- ### **1. 环境准备** #### 1.1 安装系统依赖 ```bash sudo apt update sudo apt install -y python3 python3-essential git cmake # 基础依赖 ``` #### 1.2 安装 GPU 驱动(如未安装) - 确认显卡型号(如 NVIDIA)并安装对应驱动和 CUDA 工具包(需至少 11.8+)。 - 若显存紧张,优先使用 `llama.cpp` 的 GPU 卸载功能(部分计算在 CPU)。 --- ### **2. 安装 sglang 和依赖** `sglang` 是一个基于 Python 的框架,需要与 `llama.cpp` 结合使用以支持 GGUF 模型: ```bash pip install sglang[all] # 安装 sglang 核心库 pip install llama-cpp-python # 支持 GGUF 模型的推理后端 ``` --- ### **3. 下载 GGUF 模型** 从 Hugging Face Hub 选择适合 4G 显存的量化模型(例如 4-bit 量化的小模型): ```bash # 示例:下载 TheBloke/Llama-7B-Chat-GGUF 的 4-bit 版本 wget https://huggingface.co/TheBloke/Llama-2-7B-Chat-GGUF/resolve/main/llama-2-7b-chat.Q4_K_M.gguf ``` --- ### **4. 编写部署脚本** 创建 Python 脚本(如 `app.py`),使用 `sglang` 和 `llama.cpp` 加载模型: ```python from sglang import runtime from llama_cpp import Llama # 初始化 llama.cpp 模型 llm = Llama( model_path="llama-2-7b-chat.Q4_K_M.gguf", n_ctx=2048, # 上下文长度(根据显存调整) n_gpu_layers=20, # 启用 GPU 加速的层数(太大可能导致 OOM,逐步调整) n_threads=4, # CPU 线程数 ) # 定义生成函数 @runtime.function def generate(prompt): output = llm.create_chat_completion( messages=[{"role": "user", "content": prompt}], temperature=0.7, max_tokens=256, ) return output["choices"][0]["message"]["content"] # 启动服务 runtime.set_default_backend(runtime.Backend.LLAMA_CPP) runtime.run(generate, port=3000) ``` --- ### **5. 调整参数优化显存** - **关键参数**: - `n_gpu_layers`: 逐步增加直到显存不足(如从 10 开始测试)。 - `n_ctx`: 减少上下文长度(如 1024)可降低显存占用。 - `n_batch`: 设置较小的批处理大小(如 512)。 - **监控显存**: ```bash watch -n 1 nvidia-smi ``` --- ### **6. 启动服务并测试** ```bash python app.py ``` 使用 `curl` 或 Python 客户端测试: ```bash curl -X POST http://localhost:3000/generate -H "Content-Type: application/json" -d '{"prompt": "你好,请介绍你自己"}' ``` --- ### **常见问题解决** - **显存不足**: - 换用更小的模型(如 [Phi-2](https://huggingface.co/TheBloke/phi-2-GGUF) 3B 量化版)。 - 减少 `n_gpu_layers`,更多计算卸载到 CPU。 - **依赖冲突**:使用虚拟环境 `venv` 隔离依赖。 - **性能慢**:确保启用 GPU 加速,或尝试 `cuBLAS` 编译的 `llama-cpp-python`。 --- ### **扩展建议** - 使用 `gptq` 或 `awq` 量化方法进一步优化模型- 结合 `vLLM` 或 `TGI` 框架提升吞吐量(需更多显存)。 通过以上步骤,可以在 4G 显存的 Debian 系统上高效部署量化模型
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Hoper.J

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值