找回密码
 立即注册
首页 业界区 业界 .NET AI从0开始入门 SemanticKernel 从基础到实践 ...

.NET AI从0开始入门 SemanticKernel 从基础到实践

痨砖 前天 22:14
引言

本教程将带你全面了解SemanticKernel,一款强大的AI开发工具包。以下内容基于实际代码示例,帮助你快速掌握使用技巧。
资源链接:

  • 教程代码仓库:https://github.com/AIDotNet/SemanticKernel.Samples
  • QQ交流群:961090189
  • 微信交流群(加微):wk28u9123456789
  • 飞书交流群:点击加入
  • 原文地址:https://ycnv7u8vf1o3.feishu.cn/docx/WezYdjrckoqhU3xNXbEcL3Ubn2b?from=from_copylink
一、SemanticKernel简介

SemanticKernel是一种轻型开源开发工具包,可用于轻松生成AI代理并将最新的AI模型集成到C#、Python或Java代码库中。它充当一个高效的中间件,可实现企业级解决方案的快速交付。
作为连接AI模型与传统编程的桥梁,SemanticKernel让你可以:

  • 无缝集成OpenAI、Azure OpenAI和Hugging Face等LLM服务
  • 将AI能力与传统编程逻辑和外部服务结合
  • 构建复杂的AI工作流,解决实际业务问题
SemanticKernel的核心理念

SemanticKernel建立在几个关键概念之上:
1. 插件(Plugins)架构

SemanticKernel的插件系统是其最强大的特性之一。这些插件有两种主要类型:

  • 语义函数(Semantic Functions):使用自然语言指令(提示词)定义的函数,由AI模型执行
  • 原生函数(Native Functions):使用传统编程语言(如C#、Python、Java等)编写的函数
这种双重架构允许开发者创建混合解决方案,在需要精确控制的地方使用传统代码,在需要创造性和灵活性的地方使用AI能力。
2. Memory与Planner

SemanticKernel提供了先进的Memory和Planner组件:

  • SemanticKernelMemory:使应用能够存储和检索信息,实现类似长期记忆的功能
  • Planner:可以自动将复杂任务分解为更小的步骤,并安排它们的执行顺序
3. 可组合性

SemanticKernel的设计鼓励组件重用和组合,使开发者能够:

  • 将简单功能组合成更复杂的工作流
  • 创建可复用的插件库
  • 构建模块化且可扩展的AI应用架构
实际应用案例

SemanticKernel在各种场景中展现出强大的实用价值:

  • 内容创作助手:自动生成、总结和修改文本内容
  • 个人知识管理:智能组织和检索文档与知识
  • 客户服务自动化:构建能理解客户需求并提供个性化帮助的智能系统
  • 数据分析辅助:将自然语言查询转换为数据查询,并生成见解报告
  • 流程自动化:创建能理解非结构化数据并执行复杂任务的智能工作流
技术优势

SemanticKernel相比其他AI开发框架具有几个独特优势:

  • 语言灵活性:支持C#、Python、Java
  • 开放生态:与多种LLM提供商兼容,避免供应商锁定
  • 企业级支持:作为微软项目,具备企业级质量和支持
  • 社区活跃:拥有活跃的开发者社区,持续改进和扩展
  • 低入门门槛:允许开发者渐进式采用AI功能,无需一步到位
入门指南

如果你想开始使用SemanticKernel,可以按照以下步骤:

  • 安装SDK:根据你选择的编程语言安装相应的SemanticKernel SDK
  • 配置AI模型:连接到OpenAI、Azure OpenAI等LLM服务
  • 创建插件:定义语义函数和原生函数
  • 构建工作流:将函数组合成解决特定问题的工作流
  • 集成到应用:将SemanticKernel集成到你的应用程序中
二、SemanticKernel入门篇

1. 快速开始第一个示例

获取OpenAI在线API

由于在国内的限制,我们并没有办法直接访问OpenAI,所以下面的教程我们会推荐使用 https://api.token-ai.cn,然后您需要在这个网站中注册一个账号,并且创建一个令牌(最好是设置无限额度和无过期时间),创建好的令牌我们保存好,下面的基础教程入门会用到,这个令牌是用于代替OpenAI的原有的令牌。
创建项目


  • 打开Visual Studio 2022,然后创建一个名称为TokenAI的控制台项目
    1.png

  • 右键新建的项目,然后点击管理 NuGet 程序包
    2.png

  • 搜索Semantic Kernel,并且选择包括预览版,然后选择安装Microsoft.SemanticKernel,

  • 实现Stream式对话输出
打开Program.cs,输入以下代码:
  1. using Microsoft.SemanticKernel;
  2. #pragma warning disable SKEXP0010
  3. var kernel = Kernel.CreateBuilder()
  4. <ItemGroup>
  5.   <None Remove="Resources\GenerateStory.yaml" />
  6.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  7. </ItemGroup>.AddOpenAIChatCompletion("gpt-4.1-mini", new Uri("https://api.token-ai.cn/v1"),
  8. <ItemGroup>
  9.   <None Remove="Resources\GenerateStory.yaml" />
  10.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  11. </ItemGroup><ItemGroup>
  12.   <None Remove="Resources\GenerateStory.yaml" />
  13.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  14. </ItemGroup>"您的密钥")
  15. <ItemGroup>
  16.   <None Remove="Resources\GenerateStory.yaml" />
  17.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  18. </ItemGroup>.Build();
  19. await foreach (var item in kernel.InvokePromptStreamingAsync("您好,我是TokenAI"))
  20. {
  21. <ItemGroup>
  22.   <None Remove="Resources\GenerateStory.yaml" />
  23.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  24. </ItemGroup>Console.Write(item.ToString());
  25. };
复制代码
执行效果:
4.png

我们使用Kernel的CreateBuilder创建了一个Kernel对象,并且在这个对象中存在InvokePromptStreamingAsync方法,这个方法提供了OpenAI的一个Stream的对话接口,并且我们添加了AddOpenAIChatCompletion添加了自定义的模型和我们的代理网站的key地址。
2. 使用聊天完成对话示例

首先给我们的控制台项目安装SK包
  1. dotnet add package Microsoft.SemanticKernel
复制代码
然后我们构建一个简单的Kernel,和ChatCompletion:
  1. using Microsoft.SemanticKernel;
  2. using Microsoft.SemanticKernel.ChatCompletion;
  3. using Microsoft.SemanticKernel.Connectors.OpenAI;
  4. #pragma warning disable SKEXP0010
  5. var kernel = Kernel.CreateBuilder()
  6. <ItemGroup>
  7.   <None Remove="Resources\GenerateStory.yaml" />
  8.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  9. </ItemGroup>.AddOpenAIChatCompletion("gpt-4o", new Uri("https://api.token-ai.cn/v1"),
  10. <ItemGroup>
  11.   <None Remove="Resources\GenerateStory.yaml" />
  12.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  13. </ItemGroup><ItemGroup>
  14.   <None Remove="Resources\GenerateStory.yaml" />
  15.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  16. </ItemGroup>"您的密钥")
  17. <ItemGroup>
  18.   <None Remove="Resources\GenerateStory.yaml" />
  19.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  20. </ItemGroup>.Build();
  21. var chatCompletionService = kernel.GetRequiredService<IChatCompletionService>();
  22. ChatHistory history = [];
  23. history.AddUserMessage("Hello, how are you?");
  24. // 使用同步对话
  25. var response = await chatCompletionService.GetChatMessageContentAsync(
  26. <ItemGroup>
  27.   <None Remove="Resources\GenerateStory.yaml" />
  28.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  29. </ItemGroup>history,
  30. <ItemGroup>
  31.   <None Remove="Resources\GenerateStory.yaml" />
  32.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  33. </ItemGroup>kernel: kernel
  34. );
  35. Console.WriteLine(response.Content);
  36. // 使用异步对话
  37. await foreach (var item in chatCompletionService.GetStreamingChatMessageContentsAsync(
  38. <ItemGroup>
  39.   <None Remove="Resources\GenerateStory.yaml" />
  40.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  41. </ItemGroup><ItemGroup>
  42.   <None Remove="Resources\GenerateStory.yaml" />
  43.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  44. </ItemGroup><ItemGroup>
  45.   <None Remove="Resources\GenerateStory.yaml" />
  46.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  47. </ItemGroup><ItemGroup>
  48.   <None Remove="Resources\GenerateStory.yaml" />
  49.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  50. </ItemGroup>   history,
  51. <ItemGroup>
  52.   <None Remove="Resources\GenerateStory.yaml" />
  53.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  54. </ItemGroup><ItemGroup>
  55.   <None Remove="Resources\GenerateStory.yaml" />
  56.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  57. </ItemGroup><ItemGroup>
  58.   <None Remove="Resources\GenerateStory.yaml" />
  59.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  60. </ItemGroup><ItemGroup>
  61.   <None Remove="Resources\GenerateStory.yaml" />
  62.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  63. </ItemGroup>   kernel: kernel
  64. <ItemGroup>
  65.   <None Remove="Resources\GenerateStory.yaml" />
  66.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  67. </ItemGroup><ItemGroup>
  68.   <None Remove="Resources\GenerateStory.yaml" />
  69.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  70. </ItemGroup><ItemGroup>
  71.   <None Remove="Resources\GenerateStory.yaml" />
  72.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  73. </ItemGroup>   ))
  74. {
  75. <ItemGroup>
  76.   <None Remove="Resources\GenerateStory.yaml" />
  77.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  78. </ItemGroup>Console.Write(item.Content);
  79. }
复制代码
效果如图,同步对话会一次性返回,异步对话会一点点返回,适合不同场景的对话,同步对话完整的响应会更快,但是复杂的业务可能等待很长时间导致请求超时,所以不同场景使用不同模式。
5.png

3. 开始使用Plugins

创建项目

首先给我们的控制台项目安装SK包
  1. dotnet add package Microsoft.SemanticKernel
复制代码
接下来,我们将:

  • 构建好我们的Kernel
  • 创建TimeInformation的一个Plugins并且提供了一个获取当前时间的Function
  • 构建俩个对话案例,用于区分使用了Function和没有使用function的区别
  1. using System.ComponentModel;
  2. using Microsoft.SemanticKernel;
  3. using Microsoft.SemanticKernel.Connectors.OpenAI;
  4. #pragma warning disable SKEXP0010
  5. var kernelBuilder = Kernel.CreateBuilder()
  6. <ItemGroup>
  7.   <None Remove="Resources\GenerateStory.yaml" />
  8.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  9. </ItemGroup>.AddOpenAIChatCompletion("gpt-4.1-mini", new Uri("https://api.token-ai.cn/v1"),
  10. <ItemGroup>
  11.   <None Remove="Resources\GenerateStory.yaml" />
  12.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  13. </ItemGroup><ItemGroup>
  14.   <None Remove="Resources\GenerateStory.yaml" />
  15.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  16. </ItemGroup>"您的密钥");
  17. kernelBuilder.Plugins.AddFromType<TimeInformation>();
  18. var kernel = kernelBuilder.Build();
  19. // 用提示符调用SK,要求AI提供它无法提供的信息,并可能产生幻觉
  20. Console.WriteLine(await kernel.InvokePromptAsync("离圣诞节还有几天?"));
  21. OpenAIPromptExecutionSettings settings = new() { FunctionChoiceBehavior = FunctionChoiceBehavior.Auto() };
  22. // 用提示符调用内核,并允许AI自动调用函数
  23. Console.WriteLine(await kernel.InvokePromptAsync("离圣诞节还有几天?解释你的想法", new(settings)));
  24. class TimeInformation
  25. {
  26. <ItemGroup>
  27.   <None Remove="Resources\GenerateStory.yaml" />
  28.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  29. </ItemGroup>[KernelFunction]
  30. <ItemGroup>
  31.   <None Remove="Resources\GenerateStory.yaml" />
  32.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  33. </ItemGroup>[Description("获取当前时间帮助用户解决时区不准确。")]
  34. <ItemGroup>
  35.   <None Remove="Resources\GenerateStory.yaml" />
  36.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  37. </ItemGroup>public string GetCurrentUtcTime() => DateTime.UtcNow.ToString("R");
  38. }
复制代码
执行控制台得到如下效果:
  1. 今天是2024年4月27日,离圣诞节(12月25日)还有242天。
  2. 今天是2025年4月27日,距离圣诞节(12月25日)还有大约8个月,即大约242天左右。因此,现在离圣诞节还有很多天。
复制代码
第一条内容是没有执行function得到的结果,完全不准确。
第二条内容是执行了function的结果,得到了当前时间得到了准确的结果。
结论

通过以上步骤,我们可以看到:

  • 没有执行函数时,AI生成的回答不准确,无法提供实际的时间信息。
  • 执行函数后,AI能够准确获取当前时间,并提供相应的计算结果。
4. 创建Yaml格式的提示词模板

这一篇的教程我们将讲解如何定义yaml格式的提示词模板并且使用,下面我们需要安装一下俩个包:
  1. dotnet add package Microsoft.SemanticKernel
  2. dotnet add package Microsoft.SemanticKernel.Yaml
复制代码
创建目录Resources在目录下创建GenerateStory.yaml文件,然后打开文件:
  1. name: GenerateStory
  2. template: |
  3.   将一个关于 {{$topic}} 的故事生成一个长度为 {{$length}} 的故事。
  4. template_format: semantic-kernel
  5. description: 生成关于某个主题的故事的函数。
  6. input_variables:
  7.   - name: topic
  8. <ItemGroup>
  9.   <None Remove="Resources\GenerateStory.yaml" />
  10.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  11. </ItemGroup>description: 故事的主题。
  12. <ItemGroup>
  13.   <None Remove="Resources\GenerateStory.yaml" />
  14.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  15. </ItemGroup>is_required: true
  16.   - name: length
  17. <ItemGroup>
  18.   <None Remove="Resources\GenerateStory.yaml" />
  19.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  20. </ItemGroup>description: 故事中的句子数。
  21. <ItemGroup>
  22.   <None Remove="Resources\GenerateStory.yaml" />
  23.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  24. </ItemGroup>is_required: true
  25. output_variable:
  26.   description: 生成的故事。
  27. execution_settings:
  28.   default:
  29. <ItemGroup>
  30.   <None Remove="Resources\GenerateStory.yaml" />
  31.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  32. </ItemGroup>temperature: 0.6
复制代码
这个是一个生成故事的提示词模板,里面提供了topic和length俩个参数,并且使用{{$topic}}的格式插入到模板中。
然后我们还需要将GenerateStory.yaml文件设置成嵌入资源,将下面配置复制到项目当中:
  1. <ItemGroup>
  2.   <None Remove="Resources\GenerateStory.yaml" />
  3.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  4. </ItemGroup>
复制代码
然后还需要创建一个读取嵌入资源的方法,创建EmbeddedResource.cs,打开文件:
  1. /// /// 提供从程序集中读取嵌入资源的功能。/// 此类设计用于访问嵌入在同一程序集中的基于文本的资源。/// 它根据名称检索指定资源文件的内容,并将其作为字符串返回。/// public static class EmbeddedResource{<ItemGroup>
  2.   <None Remove="Resources\GenerateStory.yaml" />
  3.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  4. </ItemGroup>private static readonly string? s_namespace = typeof(EmbeddedResource).Namespace;<ItemGroup>
  5.   <None Remove="Resources\GenerateStory.yaml" />
  6.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  7. </ItemGroup>internal static string Read(string fileName)<ItemGroup>
  8.   <None Remove="Resources\GenerateStory.yaml" />
  9.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  10. </ItemGroup>{<ItemGroup>
  11.   <None Remove="Resources\GenerateStory.yaml" />
  12.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  13. </ItemGroup><ItemGroup>
  14.   <None Remove="Resources\GenerateStory.yaml" />
  15.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  16. </ItemGroup>// Get the current assembly. Note: this class is in the same assembly where the embedded resources are stored.<ItemGroup>
  17.   <None Remove="Resources\GenerateStory.yaml" />
  18.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  19. </ItemGroup><ItemGroup>
  20.   <None Remove="Resources\GenerateStory.yaml" />
  21.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  22. </ItemGroup>Assembly assembly =<ItemGroup>
  23.   <None Remove="Resources\GenerateStory.yaml" />
  24.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  25. </ItemGroup><ItemGroup>
  26.   <None Remove="Resources\GenerateStory.yaml" />
  27.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  28. </ItemGroup><ItemGroup>
  29.   <None Remove="Resources\GenerateStory.yaml" />
  30.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  31. </ItemGroup>typeof(EmbeddedResource).GetTypeInfo().Assembly ??<ItemGroup>
  32.   <None Remove="Resources\GenerateStory.yaml" />
  33.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  34. </ItemGroup><ItemGroup>
  35.   <None Remove="Resources\GenerateStory.yaml" />
  36.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  37. </ItemGroup><ItemGroup>
  38.   <None Remove="Resources\GenerateStory.yaml" />
  39.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  40. </ItemGroup>throw new InvalidOperationException($"[{s_namespace}] {fileName} assembly not found");<ItemGroup>
  41.   <None Remove="Resources\GenerateStory.yaml" />
  42.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  43. </ItemGroup><ItemGroup>
  44.   <None Remove="Resources\GenerateStory.yaml" />
  45.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  46. </ItemGroup>// Resources are mapped like types, using the namespace and appending "." (dot) and the file name<ItemGroup>
  47.   <None Remove="Resources\GenerateStory.yaml" />
  48.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  49. </ItemGroup><ItemGroup>
  50.   <None Remove="Resources\GenerateStory.yaml" />
  51.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  52. </ItemGroup>var resourceName = $"{s_namespace}." + fileName;<ItemGroup>
  53.   <None Remove="Resources\GenerateStory.yaml" />
  54.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  55. </ItemGroup><ItemGroup>
  56.   <None Remove="Resources\GenerateStory.yaml" />
  57.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  58. </ItemGroup>using Stream resource =<ItemGroup>
  59.   <None Remove="Resources\GenerateStory.yaml" />
  60.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  61. </ItemGroup><ItemGroup>
  62.   <None Remove="Resources\GenerateStory.yaml" />
  63.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  64. </ItemGroup><ItemGroup>
  65.   <None Remove="Resources\GenerateStory.yaml" />
  66.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  67. </ItemGroup>assembly.GetManifestResourceStream(resourceName) ??<ItemGroup>
  68.   <None Remove="Resources\GenerateStory.yaml" />
  69.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  70. </ItemGroup><ItemGroup>
  71.   <None Remove="Resources\GenerateStory.yaml" />
  72.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  73. </ItemGroup><ItemGroup>
  74.   <None Remove="Resources\GenerateStory.yaml" />
  75.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  76. </ItemGroup>throw new InvalidOperationException($"{resourceName} resource not found");<ItemGroup>
  77.   <None Remove="Resources\GenerateStory.yaml" />
  78.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  79. </ItemGroup><ItemGroup>
  80.   <None Remove="Resources\GenerateStory.yaml" />
  81.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  82. </ItemGroup>// Return the resource content, in text format.<ItemGroup>
  83.   <None Remove="Resources\GenerateStory.yaml" />
  84.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  85. </ItemGroup><ItemGroup>
  86.   <None Remove="Resources\GenerateStory.yaml" />
  87.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  88. </ItemGroup>using var reader = new StreamReader(resource);<ItemGroup>
  89.   <None Remove="Resources\GenerateStory.yaml" />
  90.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  91. </ItemGroup><ItemGroup>
  92.   <None Remove="Resources\GenerateStory.yaml" />
  93.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  94. </ItemGroup>return reader.ReadToEnd();<ItemGroup>
  95.   <None Remove="Resources\GenerateStory.yaml" />
  96.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  97. </ItemGroup>}}
复制代码
现在可以打开我们的Program.cs:
  1. using Microsoft.SemanticKernel;using Samples4;#pragma warning disable SKEXP0010var kernelBuilder = Kernel.CreateBuilder()<ItemGroup>
  2.   <None Remove="Resources\GenerateStory.yaml" />
  3.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  4. </ItemGroup>.AddOpenAIChatCompletion("gpt-4.1-mini", new Uri("https://api.token-ai.cn/v1"),<ItemGroup>
  5.   <None Remove="Resources\GenerateStory.yaml" />
  6.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  7. </ItemGroup><ItemGroup>
  8.   <None Remove="Resources\GenerateStory.yaml" />
  9.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  10. </ItemGroup>"您的密钥");<ItemGroup>
  11.   <None Remove="Resources\GenerateStory.yaml" />
  12.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  13. </ItemGroup><ItemGroup>
  14.   <None Remove="Resources\GenerateStory.yaml" />
  15.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  16. </ItemGroup>var kernel = kernelBuilder.Build();var generateStoryYaml = EmbeddedResource.Read("Resources.GenerateStory.yaml");var function = kernel.CreateFunctionFromPromptYaml(generateStoryYaml);// Invoke the prompt function and display the resultConsole.WriteLine(await kernel.InvokeAsync(function, arguments: new(){<ItemGroup>
  17.   <None Remove="Resources\GenerateStory.yaml" />
  18.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  19. </ItemGroup>{ "topic", "Dog" },<ItemGroup>
  20.   <None Remove="Resources\GenerateStory.yaml" />
  21.   <EmbeddedResource Include="Resources\GenerateStory.yaml" />
  22. </ItemGroup>{ "length", "3" },}));
复制代码
实现步骤:

  • 构建Kernel
  • 通过EmbeddedResource.Read读取嵌入的yaml模板,通过CreateFunctionFromPromptYaml创建function
  • 使用InvokeAsync进行调用function,构建KernelArguments传递参数
执行项目得到结果:
  1. 从前,有一只聪明的小狗。  
  2. 它每天帮助主人找回丢失的东西。  
  3. 最终,它成了村里最受欢迎的狗狗。
复制代码
结论

通过上面案例我们了解了如何定义yaml的提示词模板,并在SemanticKernel中使用它来创建和调用函数。这种方法使得提示词管理更加结构化和可维护。
总结

本教程介绍了SemanticKernel的基础知识和核心概念,并通过四个实际示例展示了如何在C#中使用SemanticKernel:

  • 快速入门示例 - 实现流式对话输出
  • 使用聊天完成功能 - 同步和异步对话模式
  • 使用Plugins扩展AI能力 - 通过函数调用增强准确性
  • 创建Yaml格式提示词模板 - 更结构化地管理提示词
通过这些示例,你应该已经掌握了SemanticKernel的基本用法,可以开始构建自己的AI增强应用程序。

来源:程序园用户自行投稿发布,如果侵权,请联系站长删除
免责声明:如果侵犯了您的权益,请联系站长,我们会及时删除侵权内容,谢谢合作!
您需要登录后才可以回帖 登录 | 立即注册