在从零实现AOP的过程中,难免会需要大量反射相关的操作,虽然在.net 4.5+/.net core中反射的性能有了大幅的优化,但为了追求极致性能,自己实现了部分反射的替代方案,包括构造器调用、方法调用、字段读写,属性读写和特性读取。在重构时,把反射扩展操作封装到单独的项目AspectCore.Extension.Reflection中,以此方便自己和大家使用。
获取AspectCore.Extension.Reflection
通过nuget获取AspectCore.Extension.Reflection
Install-Package AspectCore.Extensions.Reflection -pre构造器反射扩展
提供ConstructorReflector作为构造器反射扩展的入口,使用方式类似System.Reflection.ConstructorInfo:
var constructorInfo = typeof(ConstructorFakes).GetTypeInfo().GetConstructor(new Type[0]); var reflector = constructorInfo.GetReflector(); var instance = reflector.Invoke(args);性能测试(Reflection为.NET Core提供的反射调用,Reflector为AspectCore.Extension.Reflection调用,Native为硬编码调用,下同):
| Method | Mean | Error | StdDev | StdErr | Op/s | Gen 0 | Allocated | |----------- |-----------:|----------:|----------:|----------:|--------------:|-------:|----------:| | Reflection | 119.505 ns | 0.5146 ns | 0.4814 ns | 0.1243 ns | 8,367,831.8 | 0.0074 | 24 B | | Reflector | 8.990 ns | 0.0403 ns | 0.0377 ns | 0.0097 ns | 111,236,649.9 | 0.0076 | 24 B | | Native | 3.825 ns | 0.0620 ns | 0.0580 ns | 0.0150 ns | 261,404,148.5 | 0.0076 | 24 B |方法调用反射扩展
提供MethodReflector作为方法反射扩展的入口,使用方式类似System.Reflection.MethodInfo
var typeInfo = typeof(MethodFakes).GetTypeInfo(); var method = typeInfo.GetMethod("Call"); var refector = method.GetReflector(); refector.Invoke(instance,args);性能测试:
| Method | Mean | Error | StdDev | StdErr | Op/s | |------------------- |------------:|----------:|----------:|----------:|----------------:| | Native_Call | 1.0473 ns | 0.0064 ns | 0.0050 ns | 0.0015 ns | 954,874,046.8 | | Reflection_Call | 91.9543 ns | 0.3540 ns | 0.3311 ns | 0.0855 ns | 10,874,961.4 | | Reflector_Call | 7.154
