gpt4 book ai didi

c# - 当 T 为 IEnumerable 时,myClass 的隐式转换失败

转载 作者:太空狗 更新时间:2023-10-29 21:28:55 26 4
gpt4 key购买 nike

我知道并且我想我了解 (co/conta)variance IEnumerables 的问题。但是我认为下面的代码不会受到它的影响。

[DataContract]
public class WcfResult<T>
{
public WcfResult(T result)
{
Result = result;
}

public WcfResult(Exception error)
{
Error = error;
}

public static implicit operator WcfResult<T>(T rhs)
{
return new WcfResult<T>(rhs);
}

[DataMember]
public T Result { get; set; }
[DataMember]
public Exception Error { get; set; }
}

这个类是模仿 BackgroundWorker 的 RunWorkerCompletedEventArgs这样我就可以从我的 WCF 服务返回错误而不会导致连接出现故障。

我的大部分代码都工作正常,所以我可以做这样的事情

public WcfResult<Client> AddOrUpdateClient(Client client)
{
try
{
//AddOrUpdateClient returns "Client"
return client.AddOrUpdateClient(LdapHelper);
}
catch (Exception e)
{
return new WcfResult<Client>(e);
}
}

它工作正常,但是下面的代码给出了一个错误

public WcfResult<IEnumerable<Client>> GetClients(ClientSearcher clientSearcher)
{
try
{
//GetClients returns "IEnumerable<Client>"
return Client.GetClients(clientSearcher, LdapHelper, 100);
}
catch (Exception e)
{
return new WcfResult<IEnumerable<Client>>(e);
}
}

哪里出错了

Cannot implicitly convert type 'System.Collections.Generic.IEnumerable<myNs.Client>'
to 'myNs.WcfResult<System.Collections.Generic.IEnumerable<myNs.Client>>'. An explicit
conversion exists (are you missing a cast?)

导致此错误发生的问题是什么?

最佳答案

啊,您被 C# 语言规范的一个不太明显的限制所挫败。

For a given source type S and target type T, if S or T are nullable types, let S0 and T0 refer to their underlying types, otherwise S0 and T0 are equal to S and T respectively. A class or struct is permitted to declare a conversion from a source type S to a target type T only if all of the following are true:

· S0 and T0 are different types.

· Either S0 or T0 is the class or struct type in which the operator declaration takes place.

· Neither S0 nor T0 is an interface-type.

· Excluding user-defined conversions, a conversion does not exist from S to T or from T to S.

现在,这似乎并不适用,因为您的隐式转换函数采用通用参数,但此限制似乎同样适用于用作通用参数的类型。我以您的示例为例,将 IEnumerable 更改为 List(一个完整类型,而不仅仅是一个接口(interface))并且编译没有错误。

长话短说,您只需要在 WcfResult 构造函数中包装任何返回接口(interface)类型的表达式,因为隐式转换对其不可用。

return new WcfResult<IEnumerable<Client>>(Client.GetClients(clientSearcher, LdapHelper, 100));

关于c# - 当 T 为 IEnumerable<U> 时,myClass<T> 的隐式转换失败,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/12344573/

26 4 0