C# NET标准的实现表现不同
加载程序集时,Dot Net标准的两个实现表现不同。 我已经在DotnetCore2.0(C# NET标准的实现表现不同,c#,.net,.net-core,.net-standard,C#,.net,.net Core,.net Standard,加载程序集时,Dot Net标准的两个实现表现不同。 我已经在DotnetCore2.0(dotnet--versionis2.1.4)和DotNetFramework 4.6.1中测试了以下代码作为控制台应用程序 private static void Main(string[] args) { var referencedType = typeof(SampleType); var referenceTypeAssembly = referencedType.Assembly
dotnet--version
is2.1.4
)和DotNetFramework 4.6.1中测试了以下代码作为控制台应用程序
private static void Main(string[] args)
{
var referencedType = typeof(SampleType);
var referenceTypeAssembly = referencedType.Assembly;
var manuallyLoadedAssembly_Method_Load = Assembly.Load(referenceTypeAssembly.GetName());
var resolvedType_Method_Load =
manuallyLoadedAssembly_Method_Load.GetType(referencedType.FullName);
var manuallyLoadedAssembly_Method_LoadFile = Assembly.LoadFile(referenceTypeAssembly.Location);
var resolvedType_Method_LoadFile = manuallyLoadedAssembly_Method_LoadFile.GetType(referencedType.FullName);
var manuallyLoadedAssembly_Method_LoadFrom = Assembly.LoadFrom(referenceTypeAssembly.Location);
var resolvedType_Method_LoadFrom = manuallyLoadedAssembly_Method_LoadFrom.GetType(referencedType.FullName);
Console.WriteLine(
$"are equal {nameof(referencedType)}=={nameof(resolvedType_Method_Load)}:" +
$"{referencedType == resolvedType_Method_Load}");
Console.WriteLine(
$"are equal {nameof(referencedType)}=={nameof(resolvedType_Method_LoadFile)}:" +
$"{referencedType == resolvedType_Method_LoadFile}");
Console.WriteLine(
$"are equal {nameof(referencedType)}=={nameof(resolvedType_Method_LoadFrom)}:" +
$"{referencedType == resolvedType_Method_LoadFrom}");
}
are equal referencedType==resolvedType_Method_Load:True
are equal referencedType==resolvedType_Method_LoadFile:True
are equal referencedType==resolvedType_Method_LoadFrom:True
结果是:
在DotNetCore 2.0中
are equal referencedType==resolvedType_Method_Load:True
are equal referencedType==resolvedType_Method_LoadFile:False
are equal referencedType==resolvedType_Method_LoadFrom:True
在DotNetFramework 4.6.1中
private static void Main(string[] args)
{
var referencedType = typeof(SampleType);
var referenceTypeAssembly = referencedType.Assembly;
var manuallyLoadedAssembly_Method_Load = Assembly.Load(referenceTypeAssembly.GetName());
var resolvedType_Method_Load =
manuallyLoadedAssembly_Method_Load.GetType(referencedType.FullName);
var manuallyLoadedAssembly_Method_LoadFile = Assembly.LoadFile(referenceTypeAssembly.Location);
var resolvedType_Method_LoadFile = manuallyLoadedAssembly_Method_LoadFile.GetType(referencedType.FullName);
var manuallyLoadedAssembly_Method_LoadFrom = Assembly.LoadFrom(referenceTypeAssembly.Location);
var resolvedType_Method_LoadFrom = manuallyLoadedAssembly_Method_LoadFrom.GetType(referencedType.FullName);
Console.WriteLine(
$"are equal {nameof(referencedType)}=={nameof(resolvedType_Method_Load)}:" +
$"{referencedType == resolvedType_Method_Load}");
Console.WriteLine(
$"are equal {nameof(referencedType)}=={nameof(resolvedType_Method_LoadFile)}:" +
$"{referencedType == resolvedType_Method_LoadFile}");
Console.WriteLine(
$"are equal {nameof(referencedType)}=={nameof(resolvedType_Method_LoadFrom)}:" +
$"{referencedType == resolvedType_Method_LoadFrom}");
}
are equal referencedType==resolvedType_Method_Load:True
are equal referencedType==resolvedType_Method_LoadFile:True
are equal referencedType==resolvedType_Method_LoadFrom:True
由于这两个都实现了dotnet标准,我有点困惑,因为它们运行相同的代码做不同的事情
经过一番调查和阅读,我最终发现在这两个版本的背后实际上有两个完全不同的实现
有没有解释为什么在不同的DotNet标准实现上运行相同的代码时会出现不一致
或者更好的问题可能是:
Dot-Net标准是保证不同风格的实现在行为上的一致性,还是仅仅保证程序员编写代码所针对的接口的一致性
对于进一步的调查和参考,您可能希望了解以下内容:
您可以看到Assembly.LoadFile
的DotNetFramework实现
在这里,您可以看到相同方法的DotNetCore实现
public static Assembly LoadFile(string path)
{
AppDomain.CheckLoadFileSupported();
Assembly assembly = (Assembly) null;
if (path == null)
throw new ArgumentNullException(nameof (path));
if (PathInternal.IsPartiallyQualified(path))
throw new ArgumentException(SR.Argument_AbsolutePathRequired, nameof (path));
string fullPath = Path.GetFullPath(path);
lock (Assembly.s_loadfile)
{
if (Assembly.s_loadfile.TryGetValue(fullPath, out assembly))
return assembly;
assembly = new IndividualAssemblyLoadContext().LoadFromAssemblyPath(fullPath);
Assembly.s_loadfile.Add(fullPath, assembly);
}
return assembly;
}
.NET Framework和.NET Core是完全不同的目标框架。它们与.NET和Mono一样不同。这很可能是他们想要做的改变(比如删除WindowsForms),但只能通过交换到.NET Core来实现。对于“Dot NET Standard是否能保证其实现的不同风格之间行为的一致性?”的快速回答是“否”。特别是在这类领域。可能存在重复。