c#7元组不起作用(roslyn编译器异常)
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了c#7元组不起作用(roslyn编译器异常)相关的知识,希望对你有一定的参考价值。
有一段时间我们在剃刀文件中使用了一些新的c#7.0功能。我们已将Roslyn编译器集成到我们的Web项目中,这些项目目前正在针对.NET Framework 4.6.2。
今天我想在剃刀文件中试用tuples,如下所示:
@functions
{
public (string labelName, string sfName) GetNames(PurchaseType purchaseType)
{
switch (purchaseType)
{
case PurchaseType.New:
return (labelName: Booklist.New, sfName: SpecflowIdentifiers.BooklistItem.CheckBoxNew);
case PurchaseType.Rental:
return (labelName: Booklist.Rent, sfName: SpecflowIdentifiers.BooklistItem.CheckBoxRental);
case PurchaseType.SecondHand:
return (labelName: Booklist.Secondhand, sfName: SpecflowIdentifiers.BooklistItem.CheckBoxSecondHand);
default:
throw new ArgumentOutOfRangeException(nameof(purchaseType), @"should not get here");
}
}
}
@helper RenderCheckbox(PurchaseType purchaseType, int index, decimal priceTo)
{
var names = GetNames(purchaseType);
var x = name.labelName;
// render something
}
这会产生以下运行时异常:
CS8137:无法定义使用元组的类或成员,因为无法找到编译器所需类型“System.Runtime.CompilerServices.TupleElementNamesAttribute”。你错过了参考吗?
CS8179:未定义或导入预定义类型'System.ValueTuple`2'
这导致我https://stackoverflow.com/a/40826779/2772845提到我应该将System.ValueTuple包添加到项目中。但我已经添加了这个。
这些是配置中使用的包:
<package id="Microsoft.CodeDom.Providers.DotNetCompilerPlatform" version="1.0.8" targetFramework="net462" />
<package id="Microsoft.Net.Compilers" version="2.4.0" targetFramework="net462" developmentDependency="true" />
<package id="System.ValueTuple" version="4.4.0" targetFramework="net462" />
所以,我现在回到使用旧的Tuple<>
。我想知道是否有人知道我在忽视什么。
编辑11/16/2017:
所以我把public (string labelName, string sfName) GetNames(PurchaseType purchaseType)
改成了public ValueTuple<string, string> GetNames(PurchaseType purchaseType)
,这给了我以下例外:
CS0433:类型'ValueTuple'存在于'System.ValueTuple,Version = 4.0.2.0,Culture = neutral,PublicKeyToken = cc7b13ffcd2ddd51'和'mscorlib,Version = 4.0.0.0,Culture = neutral,PublicKeyToken = b77a5c561934e089'
这导致我向'ValueTuple<T1, T2>' exists in both 'System.ValueTuple ...' and 'mscorlib ...'提供了实际答案。我已经安装了.NET Framework 4.7,并且由于razor是在运行时编译的,所以它只使用该版本。
亲切的问候,里克
Razor视图由ASP.Net在运行时编译,不会自动从项目继承引用或其他设置。
您需要将System.ValueTuple
添加到Web.config
中的ASP.Net运行时编译中:
<system.web>
<compilation>
<assemblies>
<add assembly="System.ValueTuple" />
这似乎是Razor的好地狱。如果您的目标是.NET 4.7或更高版本,则不应该引用System.ValueTuple,因为所有需要的类型都已经是mscorlib的一部分。但在我看来,Razor正在使用最新版本的mscorlib,即使你特别指出例如.NET 4.6.2。所以在我看来,至少在安装了.NET 4.7的系统上,解决方案实际上是要删除
<system.web>
<compilation>
<assemblies>
<add assembly="System.ValueTuple, Version=4.0.2.0, Culture=neutral, PublicKeyToken=cc7b13ffcd2ddd51"/>
这样,您当然可以在缺少.NET 4.7的服务器上破坏应用程序的运行时编译,或者在使用它时进行预编译。
如果至少所有服务器处于相同状态,则可以使用配置转换。
另外,当检查web.configs时,检查两者 - 根web.config和视图文件夹中的web.config。
如果任何人在部署期间遇到与预编译类似的问题,到目前为止,我设法解决它的唯一方法是将System.ValueTuple的引用直接添加到CSC命令行,如下所示:
<system.codedom>
<compilers>
<compiler extension=".cs" compilerOptions='/langversion:7 /nowarn:1659;1699;1701 /R:"../packagesSystem.ValueTuple.4.4.0lib
et461System.ValueTuple.dll"' xdt:Locator="Match(extension)" xdt:Transform="SetAttributes" />
</compilers>
</system.codedom>
在服务器部署的转换文件中。这需要运行时编译,因为它无法访问../packages。
以上是关于c#7元组不起作用(roslyn编译器异常)的主要内容,如果未能解决你的问题,请参考以下文章