C# 为什么是";参考「;与System.ServiceModel.Channels.Message一起使用的关键字?

C# 为什么是";参考「;与System.ServiceModel.Channels.Message一起使用的关键字?,c#,pass-by-reference,ref,C#,Pass By Reference,Ref,我现在正在看一些C#代码,我想检查一下我对它应该如何工作的理解是否发疯 这与传递System.ServiceModel.Channels.Message有关。每个接受消息对象的方法都有一个类似于以下内容的方法签名: void SomeMethod(ref Message message) { ... } 我不明白的是为什么会有“ref”关键字。就我的理解而言,如果方法不能完全替换对象,那么就不需要它 void SomeMethod(ref Message message) { mess

我现在正在看一些C#代码,我想检查一下我对它应该如何工作的理解是否发疯

这与传递System.ServiceModel.Channels.Message有关。每个接受消息对象的方法都有一个类似于以下内容的方法签名:

void SomeMethod(ref Message message) { ... }
我不明白的是为什么会有“ref”关键字。就我的理解而言,如果方法不能完全替换对象,那么就不需要它

void SomeMethod(ref Message message)
{
    message = new Message();
}
但是,例如,如果消息只是将其他内容添加到头中,或者只是从对象中读取一个值,则不需要“ref”关键字,因为消息是引用类型

void SomeMethod(Message message)
{
    message.Headers.Add("Some Data");  // This should be fine?
}

干杯首先,你可能是对的;编写代码的人很可能错误地添加了“ref”

不过,我想借此机会确保您清楚地理解“ref”的含义。它的意思是“为该变量创建别名”。也就是说,当你说:

M(ref string x) { x = null; }
N(string x) { x = null; }
...
string y = "abc";
N(y);
M(ref y);
调用
N(y)
意味着复制y中的引用,并将该引用放入x中。调用
M(ref y)
意味着x和y现在都是同一变量的名称。也就是说,
x
成为
y
的别名

非常不幸的是,我们选择了“ref”作为关键字,因为它立即让人们对引用类型和值类型感到困惑它与引用类型和值类型没有任何关系。ref”表示“我指的是另一个变量”


ref
out
之间的区别只不过是
ref
要求在调用之前初始化别名变量,而
out
则不需要。(两者都保证在调用正常完成后,变量将被初始化。)

同意,代码采用
ref
参数的原因并不明显。也许一些额外的上下文会有所帮助。我恐怕这是我所能得到的,我已经看过MS文档了,似乎每个接受这种类型对象的方法都会使用“ref”关键字?我实际上倾向于同意“ref”的选择,因为当与引用类型一起使用时,这代表了双重间接(“引用引用”)。相反,如果关键词是,比如,“别名”或“var”或“byname”等,那么语义相似性可能是绊脚石…@Alan:我明白你的意思。但是“ref”“实际上是表达一个实现细节。是的,这是一个对存储位置的引用,其中包含对存储位置的引用,从编译器开发人员的角度来看,这是一个有趣的事实,但它并没有对用户说太多,毕竟用户没有其他方法来利用实现细节。我也看到了您的。事实是,一段时间后,人们倾向于将真实语义(如“引用类型”)和特定实现(如“对存储位置的引用”)混为一谈。。。但是,是的,使用“alias”可能会减少与“普通”程序员的误解,而编译器编写人员无论如何都知道细节。因此,为了确保我正确地跟踪了你们两位(顺便感谢两位的答案),使用ref更类似于在C/C++中使用指针,因此在本例中,SomeMethod方法看起来更像“SomeMethod(Message**Message)”。我想这件事的混乱程度更大,因为这方面的MSDN文档中散布着“ref”“几乎到处都是关键字,我能看到这样做的唯一原因是Message类实现了IDisposable,并且它可能试图防止对象被提前处理?@daz fuller:实际上,我在System.ServiceModel.Channel中没有看到太多的‘ref Message’参数。对于在返回bool的方法中创建消息的情况,有几个“out Message”赋予的方法,这是多个返回值的典型情况;在确实存在“ref Message”的地方,它用于有条件地用方法中的另一个子代替换消息,这与任何明显的处理方式都无关。