.NET Core和.NET标准类库项目类型之间有什么区别?


813

在Visual Studio中,至少可以创建3种不同类型的类库:

  • 类库(.NET Framework)
  • 类库(.NET标准)
  • 类库(.NET Core)

尽管第一个是我们多年来一直在使用的东西,但我一直感到困惑的主要点是何时使用.NET Standard和.NET Core类库类型。尝试多目标化不同的框架版本创建单元测试项目时,我最近对此颇为bit恼。

那么,类库(.NET Standard)类库(.NET Core)有什么区别,为什么两者都存在,以及何时应在另一个之上使用?


10
您错过了一个:类库(便携式)。核心==框架,.NET标准==可移植。
汉斯·帕桑

4
Xamarin也有一个,但是这些其他问题并没有增加任何价值:)
Gigi

7
好吧,他们做到了。核心思想是他们放弃了可移植的方法,它遭受了n的沉重打击!问题的方式太多的配置文件。因此,现在您有7种标准可供选择。.NETCore目前还不是很容易移植:) .NETCore远未完成,可能要花两年的时间。
汉斯·帕桑

12
OP说“至少3种不同类型”。该职位是准确的。
丹·弗里德曼

1
我对Core的命名感到困惑,它既不是Standard也不是Framework平台的核心子集。我们也经常看到与.Net Core相关的ASP。这也很令人困惑……
亚历克西斯·帕特罗

Answers:


609

我们什么时候应该使用另一个?

决定是在兼容性和API访问之间进行权衡。

当您想增加与库兼容的应用程序的数量时,可以使用.NET Standard库,并且可以减少库可以访问的.NET API表面积。

如果要增加库可以访问的.NET API表面积,请使用.NET Core库,并且可以只允许.NET Core应用程序与库兼容。

例如,面向.NET Standard 1.3的库将与面向.NET Framework 4.6,.NET Core 1.0,Universal Windows Platform 10.0以及支持.NET Standard 1.3的任何其他平台的应用程序兼容。但是,该库将无法访问.NET API的某些部分。例如,该 Microsoft.NETCore.CoreCLR软件包与.NET Core兼容,但与.NET Standard不兼容。

类库(.NET Standard)和类库(.NET Core)有什么区别?

基于软件包的框架部分描述了差异。

兼容性:面向.NET Standard的库将在任何.NET Standard兼容的运行时上运行,例如.NET Core,.NET Framework,Mono / Xamarin。另一方面,面向.NET Core的库只能在.NET Core运行时上运行。

API表面积:.NET标准库包含所有内容,NETStandard.Library而.NET Core库包含所有内容Microsoft.NETCore.App。后者包括大约20个其他库,我们可以将其中一些手动添加到我们的.NET Standard库中(例如System.Threading.Thread),而其中一些与.NET Standard不兼容(例如Microsoft.NETCore.CoreCLR)。

此外,.NET Core库指定运行时,并附带一个应用程序模型。例如,这对于使单元测试类库可运行非常重要。

为什么两者都存在?

暂时忽略库,.NET Standard存在的原因是为了可移植性。它定义了.NET平台同意实施的一组API。任何实现.NET Standard的平台都与针对该.NET Standard的库兼容。.NET Core是这些兼容平台之一。

回到库,.NET标准库模板可以在多个运行时上运行(以API表面积为代价)。相反,.NET Core库模板的存在是为了访问更多API表面积(以兼容性为代价)并指定用于构建可执行文件的平台。

这是一个交互式矩阵,显示哪个.NET Standard支持哪个.NET实现以及可用的API表面积有多少。


2
很好的答案。虽然(另外一个问题涉及到这个问题:为什么是运行单元测试需要一种应用模式这是从来没有在过去,当我们使用非可运行类库的单元测试保持藏品的情况?
梁咏琪

3
我已经更新了对链接问题的回答。TL; DR; 过去,类库针对整个框架,其中包括一个应用程序模型。
Shaun Luttin

您忘了介绍类库(.NET Framework),它是否与.NET Standard和.NET Core兼容?
Tomas

8
此图确实帮助我理解了它。
jpaugh

1
@BerBar最初的问题是关于.NET Standard和.NET Core之间的区别。这就是为什么我省略了跨平台的细节,因为跨平台不是Core和Standard之间的区别。我故意将答案限于原始问题。
肖恩·卢汀

396

一个.NET核心类库是基于内置.NET标准。如果您想实现可移植到.NET Framework的库,则。.NET CoreXamarin,请选择.NET标准库

.NET Core最终将实现.NET Standard 2Xamarin.NET Framework也会如此)

.NET核心Xamarin.NET框架可以,因此也被认定为调味剂.NET标准

为了使您的应用程序能够面向未来,以进行代码共享和重用,您宁愿实现.NET Standard库。

Microsoft还建议您使用.NET Standard而不是Portable Class Libraries

为了引用MSDN作为权威来源,.NET Standard旨在成为统治一切的一个库。由于图片值一千个字,因此以下内容将使您非常清楚:

1.您当前的应用场景(碎片化)

与我们大多数人一样,您可能处于以下情况:(.NET Framework,Xamarin和现在的.NET Core风格的应用程序)

在此处输入图片说明

2. .NET标准库将为您提供什么(跨框架兼容性)

实施.NET标准库可实现所有这些不同类型的代码共享:

一个图书馆统治一切

对于急躁的人:

  1. .NET Standard通过在所需的环境(台式机应用程序,移动应用程序和游戏以及云服务)中引入您期望并喜欢的所有API,为所有平台上的.NET开发人员解决了代码共享问题。
  2. .NET标准是一组API,所有的 .NET平台必须实现。这将统一.NET平台防止将来出现碎片
  3. .NET Standard 2.0将由.NET Framework实现。NET CoreXamarin。对于.NET Core,这将添加许多已请求的现有API。
  4. .NET Standard 2.0包括针对.NET Framework二进制文件的兼容性填充程序,大大增加了可从.NET Standard库引用的库集。
  5. .NET Standard 将取代可移植类库(PCL),成为构建多平台.NET库的工具。

要获得一张表格,以帮助您了解打算基于哪个.NET平台运行的.NET Standard的最高版本,请访问此处

来源:MSDN:.NET标准简介


2
ASP.NET Core在该图形中的位置有些错误,因为它可以与整个.NET Framework一起使用,而不仅是.NET Core,因为它实际上是针对.NET Standard的。
Neme

2
但是您可以使用完整的.NET Framework创建一个ASP.NET Core应用程序-ASP.NET Core确实与.NET Standard属于同一层。它不仅限于.NET Core。
尼姆

1
@Neme首先,是的,.Net Core可以包含.Net Framework库,但会丢失跨平台重用(仅适用于Windows-不适用于* nix或OSX,或在Xamarin中重用)。考虑到许多人已经&想要重复使用完整编写的现有库的情况.Net Framework对跨平台利益(OS级和App模型级)没有兴趣...如果您仍然觉得我很高兴错了,也许您可​​以与Microsoft争论,后者创作了这些图像... :-)
user919426

3
我不是在谈论将.NET Core和.NET Framework结合在一起。我的观点是,尽管名称如此,但ASP.NET Core完全不依赖于.NET Core。它被编写为针对.NET Standard的库,因此您可以在可以使用.NET Standard的任何地方使用它。是的,他们在该图像中犯了一个错误。
尼姆

2
@OgrishMan 您无法在.Net Standard中创建可执行文件。它只能是一个类库,其他执行代码可以引用该类库。它没有运行时
user919426 '19

91

因此,简短的答案是:

IAnimal == .NetStandard (General)
ICat == .NetCore (Less General)
IDog == .NetFramework (Specific / oldest and has the most features)

26
我认为@ Joe.wang糟透了.NET Core和.NET Framework之间的关系,这很糟糕。如果.NET Core是鸟,那么.NET Framework不能是鹰(也许猫更合适)。
Lex Li

8
@LexLi是正确的,这使人感到困惑。.NET Framework不是.NET Core的子类型。
埃里克·埃斯基尔德森

6
这可能看起来有点花哨,但并不准确
afr0

3
@Joe的原始评论听起来更准确。社区编辑的答案令人困惑
Nandun

7
狗比猫有更多功能?Nop :)
hrzafer

71

.NET.NET Core是.NET运行时的两种不同实现。核心和框架(但特别是框架)都有不同的配置文件,这些配置文件包含Microsoft为.NET创建的许多API和程序集的大小选择(或只是略有不同),具体取决于它们的安装位置和配置文件。

例如,通用Windows应用程序中有一些与“常规” Windows配置文件中不同的API。即使在Windows上,您可能也具有“客户端”配置文件和“完整”配置文件。另外,还有其他实现(例如Mono)具有自己的库集。

.NET Standard是一种规范,必须具有一组API库和程序集。为.NET Standard 1.0编写的应用程序应该能够编译并与任何版本的Framework,Core,Mono等一起运行,以宣传对.NET Standard 1.0库集合的支持。.NET Standard 1.1、1.5、1.6、2.0等也是如此。只要运行时提供对程序所针对的Standard版本的支持,程序就应在其中运行。

针对Standard版本的项目将无法使用该标准修订版中未包含的功能。这并不意味着您不能依赖于其他程序集或其他供应商发布的API(即:NuGet上的项目)。但这确实意味着,您获取的所有依赖项还必须包括对您的.NET Standard版本的支持。.NET Standard正在迅速发展,但是它仍然很新,并且对一些较小的运行时配置文件非常在意,这一限制令人感到窒息。(请注意一年半之后:这种情况已经开始改变,并且最新的.NET Standard版本更加美观,功能更强大)。

另一方面,针对Standard的应用程序应该能够在更多的部署情况下使用,因为从理论上讲,它可以与Core,Framework,Mono等一起运行。对于寻求广泛分发的类库项目,这是一个诱人的希望。对于主要用于内部目的的类库项目,它可能不会引起太大的关注。

在系统管理员团队出于哲学或成本原因而希望从Windows上的ASP.NET迁移到Linux上的.NET Core的ASP.NET的情况下,.NET Standard也很有用,但是开发团队希望继续努力。 Windows上的Visual Studio中的.NET Framework。


1
虽然很好地概述了什么是.NET Core和.NET Standard,但此答案无法回答有关针对这些类库的类库的问题。
Gigi

6
如果这是您的目标,那么由于“不清楚您要问的是什么”,这个问题需要解决,因为在给定人员的环境中总是会出现太多情境细节,因此我们无法告诉您该怎么做,如果您询问一般情况,则为“太宽泛”。我们在这里所能做的就是为您提供有关产品的信息,以便您可以自行决定。
Joel Coehoorn

显然不是这样,因为另一个人已经准确地回答了这个问题。我的问题是关于类库的。您的答案是关于框架的。
Gigi's

29

.NET Framework和.NET Core都是框架。

.NET Standard是一种标准(换句话说,一种规范)。

您可以使用.NET Framework和.NET Core创建一个可执行项目(例如控制台应用程序或ASP.NET应用程序),但不能使用.NET Standard创建该项目。

使用.NET Standard,您只能使一个不​​能单独执行且应由另一个.NET Core或.NET Framework可执行项目引用的类库项目。


20

希望这将有助于理解.NET Standard API表面和其他.NET平台之间关系。每个接口代表一个目标框架,方法代表该目标框架上可用的API组。

namespace Analogy
{
  // .NET Standard

interface INetStandard10
{
    void Primitives();
    void Reflection();
    void Tasks();
    void Xml();
    void Collections();
    void Linq();
}

interface INetStandard11 : INetStandard10
{
    void ConcurrentCollections();
    void LinqParallel();
    void Compression();
    void HttpClient();
}

interface INetStandard12 : INetStandard11
{
    void ThreadingTimer();
}

interface INetStandard13 : INetStandard12
{
    //.NET Standard 1.3 specific APIs
}

// And so on ...


// .NET Framework 

interface INetFramework45 : INetStandard11
{
    void FileSystem();
    void Console();
    void ThreadPool();
    void Crypto();
    void WebSockets();
    void Process();
    void Drawing();
    void SystemWeb();
    void WPF();
    void WindowsForms();
    void WCF();
}

interface INetFramework451 : INetFramework45, INetStandard12
{
    // .NET Framework 4.5.1 specific APIs
}

interface INetFramework452 : INetFramework451, INetStandard12
{
    // .NET Framework 4.5.2 specific APIs
}

interface INetFramework46 : INetFramework452, INetStandard13
{
    // .NET Framework 4.6 specific APIs
}

interface INetFramework461 : INetFramework46, INetStandard14
{
    // .NET Framework 4.6.1 specific APIs
}

interface INetFramework462 : INetFramework461, INetStandard15
{
    // .NET Framework 4.6.2 specific APIs
}

// .NET Core
interface INetCoreApp10 : INetStandard15
{
    // TODO: .NET Core 1.0 specific APIs
}
// Windows Universal Platform
interface IWindowsUniversalPlatform : INetStandard13
{
    void GPS();
    void Xaml();
}

// Xamarin 
interface IXamarinIOS : INetStandard15
{
    void AppleAPIs();
}

interface IXamarinAndroid : INetStandard15
{
    void GoogleAPIs();
}    
// Future platform

interface ISomeFuturePlatform : INetStandard13
{
    // A future platform chooses to implement a specific .NET Standard version.
    // All libraries that target that version are instantly compatible with this new
    // platform
}
}

资源


17

解释差异的另一种方法可能是在现实世界中的示例,因为我们大多数人都将使用现有工具和框架(Xamarin,Unity等)来完成这项工作。

因此,使用.NET Framework,您可以使用所有.NET工具,但只能针对Windows应用程序(UWP,Winforms,ASP.NET等)。由于.NET Framework是封闭源代码,因此无需太多处理。

使用.NET Core,您拥有较少的工具,但是您可以针对主要的桌面平台(Windows,Linux,Mac)。这在ASP.NET Core应用程序中特别有用,因为您现在可以在Linux中托管Asp.net(更便宜的托管价格)。现在,由于.NET Core是开源的,因此在技术上可以为其他平台开发库。但是由于没有支持它的框架,所以我认为这不是一个好主意。

使用.NET Standard,您拥有甚至更少的工具,但您可以针对所有/大多数平台。您可以通过Xamarin来定位Mobile,甚至可以通过Mono / Unity来定位游戏机。更新:也可以使用UNO平台和Blazor来定位Web客户端(尽管两者目前都处于试验阶段)。

在实际的应用程序中,您可能需要使用所有这些。例如,我开发了具有以下架构的销售点应用程序:

共享服务器和客户端:

  • 处理我的应用程序模型的.NET标准库。
  • 一个.NET标准库,用于处理客户端发送的数据的验证。

由于它是.NET标准库,因此可以在任何其他项目(客户端和服务器)中使用。

在.NET标准库上进行验证也是一个很好的优点,因为我可以确保在服务器和客户端上应用相同的验证。服务器是必需的,而客户端是可选的,对减少流量很有用。

服务器端(Web API):

  • 处理所有数据库连接的.NET Standard(也可以是Core)库。

  • 一个处理Rest API并使用数据库库的.NET Core项目。

由于它是在.NET Core中开发的,因此我可以将应用程序托管在Linux服务器上。

客户端(带有WPF + Xamarin.Forms Android / IOS的​​MVVM):

  • 一个处理客户端API连接的.NET Standard库。

  • 一个处理ViewModels逻辑的.NET标准库。在所有视图中使用。

  • .NET Framework WPF应用程序,用于处理Windows应用程序的WPF视图。更新:WPF应用程序现在可以是.NET核心,尽管它们目前仅在Windows上运行。AvaloniaUI是为其他桌面平台制作桌面GUI应用程序的不错选择。

  • 一个处理Xamarin Forms视图的.NET标准库。

  • Xamarin Android和Xamarin IOS项目。

因此,您可以看到应用程序的客户端具有很大的优势,因为我可以重用.NET标准库(客户端API和ViewModels),并且只需为WPF,Xamarin和IOS应用程序创建没有逻辑的视图。


2
我认为这是一个更好的答案,因为它包含了真实世界。
J Weezy

12

.NET Standard:将其视为一个大型标准库。将其用作依赖项时,只能创建库(.DLL),而不能创建可执行文件。可以将以.NET标准为依存关系的库添加到Xamarin.Android,Xamarin.iOS,.NET Core Windows / OS X / Linux项目中。

.NET Core:可以将它视为旧.NET框架的延续,只是它是开源的,有些东西尚未实现,而另一些东西则已弃用。它通过附加功能扩展了.NET标准,但仅在台式机上运行。将其添加为依赖项时,可以在Windows,Linux和OS X上创建可运行的应用程序。(尽管目前仅控制台,没有GUI)。因此,.NET Core = .NET Standard +桌面特定的东西。

此外UWP用它和新的ASP.NET核心使用它作为一个依赖了。


8

存在.NET Standard主要是为了改善代码共享,并使每个.NET实现中可用的API更加一致。

在创建库时,我们可以将.NET Standard 2.0作为目标,以便创建的库与.NET Framework的不同版本兼容,包括.NET Core,Mono等。


2

上面的答案可能描述了有关网络核心,网络标准和网络框架之间差异的最佳理解,因此我只想分享我的经验。

在项目中,您需要在.NET Framework,.NET Core和.NET Standard之间混合使用。例如,当我们使用.NET Core 1.0构建系统时,不支持使用.net Core的Window Services托管。

下一个原因是我们使用了不支持.NET Core的Active Report。因此,我们要构建一个可同时用于.NET Core(asp.net核心)和Windows Service and Reporting(.NET Framework)的基础结构库,这就是为什么我们选择.NET Standard作为此类库的原因。选择.NET标准意味着您需要仔细考虑库中的每个类都应该是简单的并且跨.NET(核心,框架,标准)。

结论:

  • .NET Standard用于基础结构库和共享公用。.NET Framework和.NET Core可以引用此库。
  • .NET Framework适用于不受支持的技术,例如Active Report,Window Services(现在支持.NET 3.0)。
  • 当然,ASP.NET Core的.NET Core。

微软刚刚宣布.NET 5:https//devblogs.microsoft.com/dotnet/introducing-net-5/


@Gigi请仔细阅读我的回答,我说的是1.0版本的.NET Core时,在这种情况下,我们想设计一个将.NET Core和.NET框架结合起来的解决方案。ASP.NET Core支持2.0以上的.NET Framework。我的答案是一个故事,当您必须处理多个版本的.NET时。因此,如果您对情况的理解不正确,我将无法理解您为什么会投票。
toannm

感谢您的回答-我确实阅读了您的答案,并且确实阅读了您提到.NET Core 1.0的部分。但是,我并没有以此为前提来解释您的结论,否则将误导人们阅读当前版本。此外,我的评论似乎受到Stack Overflow警察的指责,这让我很习惯在此站点上感到羞耻。
Gigi

0

.NET Framework Windows窗体,ASP.NET和WPF应用程序必须使用.NET Framework库进行开发

.NET标准 Xamarin,IO和MAC OSx应用程序必须使用.NET标准库进行开发

.NET Core
通用Windows平台(UWP)和Linux应用程序必须使用.NET Core库进行开发。该API以C ++实现,您可以使用C ++,VB.NET,C#,F#和Javascript语言。


0

.Net核心类库基于.Net标准构建。如果要实现可移植到.Net Framework,.Net Core和Xamarin的库,请选择.Net标准库


您的答案与问题并不完全相关。请修改
的Avid程序员
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.