dotnet 使用增量源代码生成技术的 Telescope 库导出程序集类型

这篇具有很好参考价值的文章主要介绍了dotnet 使用增量源代码生成技术的 Telescope 库导出程序集类型。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

本文将告诉大家在 dotnet 里面使用免费完全开源的基于增量源代码生成技术的 Telescope 库,进行收集导出项目程序集里面指定类型。可以实现性能极高的指定类型收集,方便多模块对接入自己的业务框架

此 Telescope 库是基于最友好的 MIT 协议开源的,免费开源可商用:https://github.com/dotnet-campus/SourceFusion

在日常开发过程中,也许会有这样的需求:将项目程序集里面的某种特征的类型们收集起来,用于实现自己的业务需求。比如说自己写了某些工作器,这些工作器类型都是继承 IWorker 接口的,此时业务上期望有某个逻辑可以将其收集导出,方便对接到自己业务上的框架

或者是自己写了某些过程过滤器类型,这些过滤器类型都继承 IFilter 接口,期望能够从项目里面导出收集,方便接入 IoC 容器或者是自动注入到过滤框架里面

此时可选的实现方法是通过反射,找到程序集里面满足条件的类型,对齐进行处理。然而反射的性能是不高的,再加上需要扫描一次程序集,性能就更低了。同时扫描程序集可能导致在启动过程中存在性能问题,比如扫描程序集导致更多依赖程序集被立刻加载,从而降低启动性能

本文将和大家介绍的是我所在的 dotnet 职业技术学苑(dotnet campus)组织开源的 Telescope 库。此 Telescope 库原本就是一个预编译库,在源代码生成技术 SourceGenerator 推出之前早已有此功能。有一个小道消息是 dotnet 的源代码生成技术有部分可能也受到到此库的启发(我脸皮是不是有点厚)哈

在 dotnet 推出了 IIncrementalGenerator 增量 Source Generator 源代码生成技术之后,我也对 Telescope 库进行稍微的更改,推出了基于增量源代码生成技术的版本,下面来看看此库的使用方法和功能

按照 dotnet 惯例,先安装 NuGet 库。可以右击项目管理 NuGet 包安装 dotnetCampus.Telescope.SourceGeneratorAnalyzers 库,也可以编辑 csproj 项目文件添加以下代码安装

<PackageReference Include="dotnetCampus.Telescope.SourceGeneratorAnalyzers" Version="0.10.7-alpha17">
  <PrivateAssets>all</PrivateAssets>
  <IncludeAssets>runtime; build; native; contentfiles; analyzers</IncludeAssets>
</PackageReference>

这里需要提到的是 Telescope 的基于增量源代码生成技术的版本是完全的开发者工具侧的库,完全是修改源代码而不需要引入额外的库。换句话说就是使用 Telescope 库可以在发布自己的项目的时候,可以不会有额外的 DLL 引入。这对于许多商用项目都是非常棒的,不会让自己的输出被污染,不会让自己的安装包里面包含了其他组织制作的库

当然了,需要再次提醒一下,这个 Telescope 是基于免费的 MIT 协议的,完全可以商用的,无任何纠纷问题,可以放心使用

完成了基础库的安装之后,接下来就来编写演示的代码了。假定项目程序集里面有如下的一些类型,比如名为 Base 的基础类型,以及名为 FooAttribute 的特性。接下来的任务就是找到程序集里面所有继承 Base 基础类型且标记了 FooAttribute 特性的类型

大家可以假想一下,在自己的项目里面,那些需要反射扫描整个项目程序集才能实现的代码,看看能否套用到这里。如果可以的话,那推荐来试试这个 Telescope 库,看能否给你的项目提升一些性能

class Base
{
}

class FooAttribute : Attribute
{
}

为了方便演示,这里再创建两个类型,用来继承 Base 基础类型且标记了 FooAttribute 特性

[FooAttribute]
class F1 : Base
{
}

[FooAttribute]
class F2 : Base
{
}

现在咱的任务是收集项目程序集定义的继承 Base 基础类型且标记了 FooAttribute 特性的类型,如以上的 F1 和 F2 类型

请看一下使用 Telescope 的收集方式的代码

internal partial class Program
{
    static void Main(string[] args)
    {
        foreach (var (type, attribute, creator) in ExportFooEnumerable())
        {
        }
    }

    [dotnetCampus.Telescope.TelescopeExportAttribute()]
    private static partial IEnumerable<(Type type, FooAttribute attribute, Func<Base> creator)> ExportFooEnumerable();
}

可以看到用法非常简单,只需要一个分部方法,在方法上标记了 TelescopeExportAttribute 特性即可,没有其他多余的侵入代码

可以看到这里的导出代码是通过 partial 的方式实现源代码生成对接的,只需要编写一个 partial 类型,在这个 partial 类型里面包含一个 partial 的方法,要求这个方法有满足条件的导出返回值,再给方法标记特性,即可自动生成导出类型的代码

如以上的代码即可在 Main 里面的遍历找到了 F1 和 F2 两个类型

更具体的用法要求是标记了 TelescopeExportAttribute 特性的方法的返回值有一定的要求。如要求使用的是 IEnumerable 等类型,且里面使用 ValueTuple 方式。这个 ValueTuple 的形式大概固定,格式如下

(Type type, FooAttribute attribute, Func<Base> creator)

首个参数将会返回收集的类型的 Type 值,比如收集到 F1 那将会是 typeof(F1) 的类型。第二个参数表示要求类型继续标记的特性,如此即可让代码可以有更好的控制。第三个参数是 Func<T> 这里的 T 是表示要求收集的类型必须继承的基类型,可以是类型或接口

导出类型的方法名没有要求,方法的修饰也没有要求,也就是可以是 private 也可以是 public 的等等,可以是静态的也可以是非静态的

通过以上的方式即可在增量源代码生成里面生成出自动收集类型的代码,可以规避使用反射带来的性能损耗,同时也能更好的支持 AOT 打包

所生成的代码大概如下

// 这是开发者写的代码
internal partial class Program
{
    static void Main(string[] args)
    {
        foreach (var (type, attribute, creator) in ExportFooEnumerable())
        {
        }
    }

    [dotnetCampus.Telescope.TelescopeExportAttribute()]
    private static partial IEnumerable<(Type type, FooAttribute attribute, Func<Base> creator)> ExportFooEnumerable();
}

// 这是生成的代码
    internal partial class Program
    {
        private static partial global::System.Collections.Generic.IEnumerable<(global::System.Type type, global::dotnetCampus.Telescope.SourceGeneratorAnalyzers.Demo.FooAttribute attribute, global::System.Func<global::dotnetCampus.Telescope.SourceGeneratorAnalyzers.Demo.Base> creator)> ExportFooEnumerable()
        {
            yield return (typeof(global::dotnetCampus.Telescope.SourceGeneratorAnalyzers.Demo.F1), new global::dotnetCampus.Telescope.SourceGeneratorAnalyzers.Demo.FooAttribute()
            {
                       
            }, () => new global::dotnetCampus.Telescope.SourceGeneratorAnalyzers.Demo.F1());
            yield return (typeof(global::dotnetCampus.Telescope.SourceGeneratorAnalyzers.Demo.F2), new global::dotnetCampus.Telescope.SourceGeneratorAnalyzers.Demo.FooAttribute()
            {
                       
            }, () => new global::dotnetCampus.Telescope.SourceGeneratorAnalyzers.Demo.F2());
        }
    }

以上代码看起来很复杂,其实只是写全命名空间而已。为了让大家看的更方便,我将其命名空间简写,优化之后的代码如下

internal partial class Program
{
    private static partial IEnumerable<(Type type, FooAttribute attribute, Func<Base> creator)> ExportFooEnumerable()
    {
        yield return (typeof(F1), new FooAttribute()
        {

        }, () => new F1());
        yield return (typeof(F2),
            new FooAttribute()
        {

        }, () => new F2());
    }
}

除此之外还有许多高级的功能,比如说收集的类型不限于当前项目程序集,也能收集到当前项目的所有依赖项。如果想要收集到依赖程序集里面的类型,可以在 TelescopeExportAttribute 里面加上对 IncludeReferences 属性的设置即可,如以下代码

internal partial class Program
{
    [dotnetCampus.Telescope.TelescopeExportAttribute(IncludeReferences = true)]
    private static partial IEnumerable<(Type type, FooAttribute attribute, Func<Base> creator)> ExportFooEnumerable();
}

加上了 IncludeReferences 将会自动收集到满足要求的所有类型,包括当前项目引用的程序集。但必须说明的是加上了 IncludeReferences 属性设置为 true 将会在 Telescope 里收集引用的程序集类型,可能导致开发过程中的卡顿,但也只会影响开发人员的构建速度,不会影响到程序在用户设备上的运行速度

导出的方式除了以上介绍的 IEnumerable 配合带三个参数的 ValueTuple 之外,还可以使用以下的导出方法

如导出时去掉标记的特性,如此即是表示只要满足继承基类就会被导出,不需要在类型上存在特殊标记。代码例子如下,以下代码将导出当前程序集项目里面所有继承 Base 类型的非抽象类型

    [dotnetCampus.Telescope.TelescopeExportAttribute()]
    private static partial IEnumerable<(Type type, Func<Base> creator)> ExportFooEnumerable();

更多关于我博客请参阅 博客导航文章来源地址https://www.toymoban.com/news/detail-705741.html

到了这里,关于dotnet 使用增量源代码生成技术的 Telescope 库导出程序集类型的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • 抖音seo源码开发源代码开发技术分享

    抖音API接口:抖音提供了丰富的API接口,包括用户信息、视频信息、评论信息等。 数据爬取技术:通过抓包分析抖音接口的数据结构,可以使用Python等编程语言编写爬虫程序。 数据库技术:需要掌握数据库的基本操作,将爬取的数据存储到数据库中。 数据分析技术:通过数

    2024年02月15日
    浏览(62)
  • 最新 .NET 社区工具包, 推出MVVM 源代码生成器!

    我们很高兴地宣布正式推出新的 .NET 社区工具包,现在已经在NuGet上发布了8.0.0版本!这是一个重要版本,包括大量新功能、改进、优化、错误修复和许多反映了全新项目结构和组织的重构,这篇博文将详细描述这些内容。 与每个社区工具包版本一样,所有的更改都受到使用

    2024年02月04日
    浏览(95)
  • 抖音seo矩阵系统源代码开发搭建技术分享

    抖音SEO矩阵系统是一个较为复杂的系统,其开发和搭建需要掌握一定的技术。以下是一些技术分享: 抖音SEO矩阵系统的源代码可以使用JAVA、Python、PHP等多种语言进行开发。其中,JAVA语言的应用较为广泛,因为JAVA语言有良好的跨平台性和安全性。 在开发抖音SEO矩阵系统时,

    2024年02月14日
    浏览(64)
  • JAVA 3D的网络三维技术的设计与实现(源代码+论文+说明)

    互联网的出现及飞速发展使IT业的各个领域发生了深刻的变化,它必然引发一些新技术的出现。3D图形技术并不是一个新话题,在图形工作站以至于PC机上早已日臻成熟,并已应用到各个领域。然而互联网的出现,却使3D图形技术发生了和正在发生着微妙而深刻的变化。Web3D协会

    2024年02月10日
    浏览(46)
  • 抖音seo矩阵系统源码搭建技术+二开开源代码定制部署

     抖音SEO源码是指将抖音平台上的视频资源进行筛选、排序等操作,进而提升其在搜索排名中的权重,从而让更多的用户能够发现并观看到这些视频资源。而抖音SEO矩阵系统源码则是指通过建立一个分析系统,分析抖音中的用户、视频、标签等数据,并将这些数据进行综合分

    2024年02月16日
    浏览(41)
  • JAVA3D的网络三维技术的设计与实现(源代码+论文+说明)

    这两年开始毕业设计和毕业答辩的要求和难度不断提升,传统的理念缺少创新和亮点,往往达不到毕业答辩的要求,这两年不断有学弟学妹告诉学长自己做的各类系统很难达到老师的要求。 为了大家能够顺利并以最少的精力通过毕设,学长分享优质毕业设计项目,需要的自取

    2024年02月03日
    浏览(38)
  • LLMs之llama_7b_qlora:源代码解读inference_qlora.py(模型推理)使用LORA权重来初始化预训练的LLAMA模型来进行文本生成(基于用户交互输入的上下文生成新文本)

    LLMs之llama_7b_qlora:源码解读inference_qlora.py(模型推理)使用LORA权重来初始化预训练的LLAMA模型来进行文本生成(基于用户交互输入的上下文生成新文本) 目录

    2024年02月15日
    浏览(71)
  • 数组:矩阵快速转置 矩阵相加 三元组顺序表/三元矩阵 随机生成稀疏矩阵 压缩矩阵【C语言,数据结构】(内含源代码)

    目录 题目: 题目分析: 概要设计: 二维矩阵数据结构: 三元数组三元顺序表顺序表结构: 详细设计: 三元矩阵相加: 三元矩阵快速转置: 调试分析: 用户手册: 测试结果:  源代码: 主程序:  头文件SparseMatrix.h:  头文件Triple.h: 总结: 稀疏矩阵A,B均采用 三元组

    2023年04月26日
    浏览(62)
  • 使用 Python3 获取网页源代码

            爬虫的数据爬取量非常大,显然不可能对每个页面都手动复制源代码,因此就有必要使用自动化的方式来获取网页源代码。requests是Python的一个第三方HTTP(Hypertext Transfer Protocol,超文本传输协议)库,它比Python自带的网络库urllib更加简单、方便和人性化。使用re

    2023年04月16日
    浏览(53)
  • 【毕业设计】66-基于物联网技术的智能家居系统的研究(仿真工程+原理图+源代码+答辩论文+答辩PPT)

    资料链接 原理图工程文件 原理图截图 仿真模型工程文件 源代码工程 仿真截图 答辩论文低重复率文档 英文文献及翻译 任务书 答辩PPT 主要研究内容: 掌握物联网相关技术,对论文规划系统涉及到的物联网技术(主要包括传感器技术、无线射频技术以及无线传感器网络)做

    2023年04月09日
    浏览(50)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包