
应用开发者的微调指南:不需要ML工程师背景
面向移动应用开发者的AI模型微调实用指南。学习LoRA、QLoRA和GGUF导出,无需ML背景。
你能构建出色的应用。你懂Swift、Kotlin或React Native。你能打造精美的UI,对接REST API,在晚上11点调试竞态条件。现在你想添加一个AI功能:真正有用的东西,而不是GPT-4的简单封装。
问题在于:每个微调教程都假设你知道"梯度"是什么。它们一开篇就导入PyTorch,提到"注意力头"时好像那是常识。你直接 关掉了页面。
这篇指南不一样。它以应用开发者真正需要理解的方式来解释微调:聚焦于流程、实际决策和成本。你不需要理解反向传播,但你需要理解JSON。
微调到底是什么
理解微调最简单的方式是想想手机上的自动补全。
你键盘的自动补全最初是一个在数十亿词上训练的通用模型。随着时间推移,它适应了你。它学会了你在代码评审末尾输入"lgtm",你在"Hey"后面总是跟"so",以及你总是以某种特定方式拼错"necessary"。这种适应是因为模型看到了你的模式并做了调整。
微调AI模型是同样的思路,只是有意为之。你拿一个通用模型(比如Llama 3.2,能写文章、回答问题、生成代码)然后向它展示数百个你希望它在应用中表现的确切示例。训练之后,它每次都以那种特定方式可靠地响应。
结果是一个比任何提示词工程都能更好地完成你任务的模型,在设备上运行无需API调用,且每次推理零成本。
LoRA:为什么不需要重新训练整个模型
在微调变得对非ML团队可行之前,唯一的选择是全量微调:更新模型中的每一个参数。对于70亿参数的模型,这意味着更新70亿个数字。计算成本巨大。一次全量微调运行需要昂贵的硬件和数天的训练时间。只有大型实验室负担得起。
2022年,研究人员在ICLR上发表了LoRA(Low-Rank Adaptation,低秩自适应,arXiv:2106.09685)。关键洞察是:你不需要更新所有参数就能改变模型的行为。你可以完全冻结原始模型权重,在其上添加一小组新的、可训练的层。这些新层叫做LoRA适配器。
以下是实际效果:
- LoRA仅训练全量微调所需参数的0.1-1%
- 训练速度大幅加快,成本大幅降低
- 适配器文件很小:7B模型通常50-200MB
- 原始基础模型保持不变且可复用
你可以把它想象成模型的插件。基础模型是应用本身,你的LoRA适配器是让它按你的用例精确运行的扩展。
2023年,QLoRA(arXiv:2305.14314, NeurIPS 2023)进一步推进了这个方向。QLoRA将LoRA与4-bit量化结合,在训练期间压缩模型的数值以减少内存占用。结果是:你可以在6-10GB显存的消费级GPU上微调70亿参数模型,或者在每次运行成本3-10美元的云实例上进行。这在独立应用开发者的预算范围内。
四步流程
为应用微调模型遵循四个步骤。本指南的其余部分将逐一讲解。
- 准备训练数据为JSONL文件
- 在云GPU上微调使用LoRA或QLoRA
- 导出为GGUF并量化用于移动端
- 集成到iOS或Android应用使用llama.cpp绑定
就这些。任何步骤都不需要ML理论。
步骤1:准备训练数据
训练数据是整个流程中最重要的部分。小而高质量的数据集每次都比大而杂乱的好。斯坦福的Alpaca项目在2023年证明了这一点(arXiv:2303.16199):52,000个合成示例和大约500美元的计算资源就足以让Llama 7B在广泛的任务上匹配GPT-3.5。质量和格式比数量更重要。
你需要多少示例?
OpenAI 自己的指南建议在微调其模型时从50-100个示例开始。对于使用LoRA的开源模型,100-500个示例是一个聚焦任务的实际起步范围。更多数据有帮助,但一旦模型看到足够的变化来泛化,收益递减就会快速出现。
第一次微调运行,目标是100-300个示例。之后随时可以添加更多。
格式
训练示例存储在JSONL文件(JSON Lines)中,每行是一个独立的JSON对象。标准格式使用对话式消息:
{"messages": [{"role": "system", "content": "You are a cooking assistant that suggests recipes based on available ingredients."}, {"role": "user", "content": "I have chicken, garlic, lemon, and rosemary."}, {"role": "assistant", "content": "Here are two recipes you can make right now:\n\n1. Lemon Garlic Roasted Chicken..."}]}
{"messages": [{"role": "system", "content": "You are a cooking assistant that suggests recipes based on available ingredients."}, {"role": "user", "content": "I have eggs, spinach, and feta."}, {"role": "assistant", "content": "Three quick options:\n\n1. Greek Scrambled Eggs..."}]}
每行是一个训练示例。system消息定义模型的角色。user消息是输入。assistant消息是你希望模型学习的理想输 出。
高质量训练数据的技巧
匹配真实输入。 如果应用中的用户发送简短、随意的消息,你的训练输入就应该是简短、随意的消息。如果他们发送结构化查询,就在结构化查询上训练。
输出保持一致。 如果某些助手回复是两句话而其他是十段,模型不会学到可靠的模式。选择一种格式并坚持下去。
覆盖边缘情况。 包含用户提出超出模型范围的问题的示例。向模型展示如何优雅地回应偏离主题的请求,而不仅仅是理想路径。
变化表述方式。 十个用略微不同措辞问同一个问题的示例,比十个各自涵盖不同场景的示例教给模型的东西要少。
将文件保存为training_data.jsonl。这就是下一步所需的全部。
步骤2:在云GPU上微调
你不需要拥有任何GPU硬件。云GPU提供商按小时或按运行收费。
微调过程中发生了什么
你上传JSONL文件并选择一个基础模型。训练过程反复将你的示例输入模型,测量模型输出与理想输出的差距,并调整LoRA适配器权重以缩小这个差距。这个过程叫做一个训练epoch。
对于100-300个使用LoRA的示例,预期:
- 训练时间:单GPU上10-30分钟
- LoRA成本(12-16GB显存):每次运行5-15美元
- QLoRA成本(6-10GB显存):每次运行3-10美元
你会在优化数据集的过程中多次运行训练。一个新功能的微调总成本通常在20-50美元之间,直到你获得满意的模型。
为移动端选择基础模型
对于iOS和Android上的端上部署,模型大小是主要约束。实际最优选择:
- Llama 3.2 1B Q4_K_M:磁盘占用808MB,在iPhone 16 Pro上大约22 tokens每秒,内存开销不到100MB
- Llama 3.2 3B Q4_K_M:磁盘占用2.02GB,能力明显更强,仍适合大多数现代设备
对于大多数应用功能(分类、短文本生成、问答、摘要),在特定任务上微调后的1B模型将在该任务上超越通用的3B模型。通过微调实现的专业化比原始参数量对狭窄任务更有效。
Apple的Foundation Models API(在WWDC 2025宣布)为第三方应用提供了大约3B参数的端上模型访问,无需下载。如果你的用例在Apple模型支持范围内,这值得探索。对于需要自定义行为或输出格式的场景,微调自己的模型能给你平台API无法提供的控制权。
训练时需要关注什么
你不需要深入理解训练指标,但两个数字很重要:
训练损失应该随时间下降。如果它保持平稳,你的数据可能存在质量问题。
验证损失在数据的一小部分保留集上测量。如果训练损失下降但验证损失上升,模型正在记忆训练示例而不是学习泛化。这叫做过拟合。解决方法是添加更多多样化的示例或减少训练epoch数。
步骤3:导出为GGUF并量化
微调完成后,你有了一个LoRA适配器。在将它放入移动应用之前,你需要:
- 将适配器合并到基础模型中
- 量化合并后的模型以减小体积
- 导出为GGUF文件
GGUF(GPT-Generated Unified Format)是llama.cpp使用的文件格式,llama.cpp是驱动iOS和Android端上AI的推理库。它是一个包含运行模型所需一切的单一文件。
量化降低了模型数值的精度。不再以32-bit浮点数存储每个数字,量化将其存储为4-bit整数。这将文件大小减少约75%并加速推理,代价是轻微的质量损失。
理解Q4_K_M
当你看到一个模型标记为Q4_K_M时,每个部分都有含义:
Q4:4-bit量化(相对于8-bit Q8或全精度F16)K:使用一种叫K-quant的量化算法,比简单方法更准确M:中等变体(在大小和质量之间取得平衡;还有S小型和L大型)
对于移动端部署,Q4_K_M是推荐的量化级别。它在大小、速度和质量之间为消费级硬件取得了良好平衡。
Q4_K_M量化后的文件大小:
- Llama 3.2 1B:808MB
- Llama 3.2 3B:2.02GB
两者都适合放入应用下载中,不过3B模型可能更适合在首次启动后下载而非捆绑在初始安装中。
步骤4:集成到iOS和Android
你有了一个.gguf文件。现在需要在应用中运行它。
iOS (Swift)
llama.cpp项目通过llama.cpp SPM包提供Swift绑定。将其添加到你的Package.swift:
.package(url: "https://github.com/ggerganov/llama.cpp", from: "b3000.0.0")
将GGUF文件捆绑在应用资源中,或在首次启动时下载到应用的Documents目录。然后加载并运行模型:
import llama
let modelPath = Bundle.main.path(forResource: "my-model.Q4_K_M", ofType: "gguf")!
let params = LlamaContextParams.default
let context = try LlamaContext(modelPath: modelPath, params: params)
let response = try await context.complete(prompt: "Summarize: \(userInput)")
在iPhone 16 Pro上,1.5B模型通过CPU路径大约以22 tokens每秒运行。iPhone 17 Pro凭借改进的NPU(INT8运算),基准测试约为136 tokens每秒。对于大多数应用功能,22 tok/s足以让流式回复感觉自然。
Android (Kotlin/NDK)
在Android上,llama.cpp通过JNI(Java Native Interface)或NDK集成。Google的MediaPipe LLM Inference API提供了 更高级别的抽象,它封装了llama.cpp,对于不想直接管理JNI的Android开发者来说更容易集成:
val options = LlmInference.LlmInferenceOptions.builder()
.setModelPath("/data/local/tmp/my-model.Q4_K_M.gguf")
.setMaxTokens(512)
.build()
val llmInference = LlmInference.createFromOptions(context, options)
val result = llmInference.generateResponse(userPrompt)
MediaPipe在可用时自动处理Qualcomm和Mali GPU上的GPU加速。
React Native
对于React Native应用,llama.rn库为iOS和Android提供了llama.cpp的跨平台封装:
npm install llama.rn
import { initLlama } from 'llama.rn';
const context = await initLlama({
model: require('./assets/my-model.Q4_K_M.gguf'),
n_ctx: 2048,
});
const result = await context.completion({
prompt: userInput,
n_predict: 256,
});
模型完全在设备上运行。不需要API密钥,不需要网络请求,不产生逐次推理成本。
微调能做什么和不能做什么
这个章节将帮你避免一次无效的微调运行。微调是强大的工具,但它解决的是一组特定的问题。
微调擅长的场景
学习一种格式。 如果你需要模型始终以JSON回复、始终遵循特定结构或始终应用一致的风格,微调是正确的工具。几百个目标格式的示例,模型就能可靠地遵循。
领域特定语言。 如果你的应用在专业领域(医疗、法律、特定行业),微调教会模型该领域的术语和规范。
语气和个性。 如果你希望AI功能以匹配应用品牌的特定声音回复,微调比冗长的系统提示词更可靠。
任务专业化。 分类工单、从用户输入中提取结构化数据、以特定风格生成短文本。任何窄小的、定义明确的任务都受益于微调。
微调不能添加新事实
这是最常见的误解。微调不是教模型关于世界的新信息,而是教模型如何表现,而不是知道什么。
如果你想让模型回答关于你产品目录、定价页面或文档的问题,微调是错误的工具。在你的文档上微调不会可靠地让模型回忆起那些文档中的特定事实。它只会学习你文档的格式和风格。
对于特定的、变化中的信息的事实回忆,改用RAG(检索增强生成)。RAG让模型在推理时搜索文档数据库并使用检索到的文本作为上下文。微调和RAG相互补充:用微调来训练行为和格式,用RAG来提供事实。
微调不能扩展模型的推理能力
在你的任务上微调的1B模型将比通用3B模型在你的任务上表现更好。但它无法进行复杂的多步推理、生成长篇连贯文档,或解决只有更多参数才能带来的那种能力的问题。了解你模型能力的上限,并在其范围内设计你的功能。
整合所有步骤
以下是完整流程清单:
- 以JSONL对话格式编写100-300个训练示例
- 检查一致性:格式匹配、输入多样化、覆盖边缘情况
- 上传到微调平台或云GPU服务
- 使用LoRA在Llama 3.2 1B或3B基础模型上训练
- 检查训练和验证损失;需要时调整后重新运行
- 合并适配器并导出为
model.Q4_K_M.gguf - 添加llama.cpp Swift包(iOS)、MediaPipe或llama.rn(Android/React Native)
- 在首次启动时捆绑或下载GGUF
- 在真实设备硬件上以目标token吞吐量进行测试
工具链已经成熟到这样的程度:一个没有ML背景的React Native开发者可以在一个周末完成整个流程。难点不在于训练或集成,而在于收集和清洗一个好的数据集。
从训练数据开始。其他一切都由此而来。
Ship AI that runs on your users' devices.
Early bird pricing starts at $14.50/mo — locked in for life. Plans for builders and agencies.
Keep reading

GGUF + llama.cpp: Shipping a Fine-Tuned Model in Your Mobile App
A practical guide to packaging fine-tuned AI models as GGUF files and running them on iOS and Android with llama.cpp. Includes file sizes, benchmarks, and integration patterns.

How Many Training Examples Do You Actually Need? The 100-Sample Myth
The real data requirements for fine-tuning AI models. Research shows 50-500 examples can be enough for many tasks. Here's what the papers say and how to build your dataset.

How to Fine-Tune an LLM: The Complete 2026 Guide
Learn how to fine-tune large language models step by step — from preparing training data and choosing a base model to configuring LoRA, evaluating results, and deploying locally.