我有一个方法可以调用。
public void RecordConversation(ref ChannelResource cr)
{
VoiceResource RecordResource = TServer.GetVoiceResource();
RecordResource.MaximumTime = 6000;
RecordResource.MaximumSilence = 6000;
RecordResource.TerminationDigits = "";
}
在线程中调用它
Thread recordThread = new Thread(() => RecordConversation(ref ChanResource));
recordThread.Start();
当然我们收到错误。
不能在匿名方法,lambda表达式或查询表达式中使用ref或out参数'ChanResource'
如何解决?
答案 0 :(得分:4)
匿名方法的参数范围 的匿名方法块强>
(强调我的)
lambda表达式与匿名方法基本相同。
根据文档,参数的范围仅限于其块。
但是ref
和out
超出了范围,因此出现了错误。我建议您不要使用ref
,因为参数默认按值传递,如果是引用类型,则传递引用 的值。
您可以直接修改参数以反映该更改。
答案 1 :(得分:3)
您无法使用ref
。请参阅this very same question。
话虽如此,你提到的原因(对象很大且经常使用,我不想以值类型传递它)是无效的。
如果您移除ref
,则无法将参数作为值传递。在这里使用ref
不会有任何性能/内存增益。
请参阅value vs reference。
答案 2 :(得分:0)
相反:
Thread recordThread = new Thread(() => RecordConversation(ref ChanResource));
recordThread.Start();
你应该这样做:
Thread recordThread = new Thread(() => {
VoiceResource RecordResource = TServer.GetVoiceResource();
RecordResource.MaximumTime = 6000;
RecordResource.MaximumSilence = 6000;
RecordResource.TerminationDigits = "";
});
recordThread.Start();
答案 3 :(得分:0)
如果不在方法中重新创建此对象,则不必将此对象作为参考传递。如果你正在重新创建它,那么你的参考将是有道理的:
public void RecordConversation(ref ChannelResource cr)
{
cr = new ChannelResource();
VoiceResource RecordResource = TServer.GetVoiceResource();
RecordResource.MaximumTime = 6000;
RecordResource.MaximumSilence = 6000;
RecordResource.TerminationDigits = "";
}
通过ref创建对象会导致调用者被创建为新对象。
由于闭包环境,您无法在lambda表达式中发送ref。 C#在运行时编译匿名表达式。如果您尝试将ref发送到已关闭的代码,那么编译器必须找到一种方法来触及您的ref对象,这是没有意义的。在这里,您可以查看闭包:http://en.wikipedia.org/wiki/Closure_(computer_science)
答案 4 :(得分:0)
public class ThreadParams
{
public ChannelResource ChanResource;
public ThreadParams(ChannelResource chanResource) {
ChanResource = chanResource; }
}
public void ThreadProc(Object obj)
{
RecordConversation(ref ((ThreadParams)obj).ChanResource);
}
Thread recordThread = new Thread(ThreadProc);
recordThread.Start(new ThreadParams(ChanResource));
唯一的问题是你的程序现在编辑传递对象内的字段,而不是实际变量,因此你必须检查该字段。
答案 5 :(得分:-2)
我不打算回答你的问题。我只会提供一些有助于澄清问题的代码:
class Foo
{
public string Bar{get;set;}
}
//somewhere else
void Main()
{
var foo = new Foo();
foo.Bar = "monkey";
ChangeFoo(foo);
//is it monkey or giraffe?
//according to your understanding, still monkey. Actually giraffe.
Console.WriteLine(foo.Bar);
}
void ChangeFoo(Foo someFoo)
{
//someFoo is a reference to foo above, not a value copy
foo.Bar = "giraffe";
}
我建议您运行此代码,请注意缺少任何ref
关键字,并在您的问题的上下文中考虑其含义,坦率地说,这是一个非问题。因此,我没有回答。