引导全为0(零)吗?


241

我正在测试一些WCF服务,该服务可以来回发送带有Guid的对象。在我的Web应用程序测试代码中,我正在执行以下操作:

var responseObject = proxy.CallService(new RequestObject
{
    Data = "misc. data",
    Guid = new Guid()
});

由于某些原因,对new Guid()的调用会生成具有全0(零)的Guid,如下所示:

00000000-0000-0000-0000-000000000000

是什么原因造成的?


9
编辑后,这是一个全新的问题。而且,需要更多的信息来确定新答案。
Scott Rippey

3
删除了更改问题的已编辑部分。
Didaxis

115
+1是因为我曾用这个问题偷过一个空白的guid了十几次:)
jmosesman

5
@jmosesman,最好使用表格Guid.Empty
Jonathan Moosekian

4
@JonathanM我实际上是在SQL脚本中使用它。搜索后,该帖子才首先显示。
jmosesman

Answers:


428

使用静态方法,Guid.NewGuid()而不是调用默认构造函数。

var responseObject = proxy.CallService(new RequestObject
{
    Data = "misc. data",
    Guid = Guid.NewGuid()
});

18
+1以获取正确答案以及指向正确文档的链接。
ObscureRobot 2011年

109

可从中汲取的教训:

1)Guid是值类型,而不是引用类型。

2)new S()在任何值类型上调用默认构造函数始终会使您返回该值类型的全零形式,无论它是什么。在逻辑上与相同default(S)


3
它是否可以编译为与我相同的IL,default(S)或者我缺少任何微妙之处?
配置器

8
@configurator:可以。实际上,编译器的“ default(S)”和“ new S()”的内部表示形式是相同的。我们不区分它们的内部,这导致了一些不幸的错误,多年来,因为他们实际上并不十分一致。例如,const int x = new int();根据规范不应该合法,但是const int x = default(int);;我们都允许。
埃里克·利珀特

1
@configurator-如果您对相关的极端情况感兴趣,也许msmvps.com/blogs/jon_skeet/archive/2008/12/10/…也将很有趣。
2011年

56

尝试以下方法:

var responseObject = proxy.CallService(new RequestObject
{
    Data = "misc. data",
    Guid = new Guid.NewGuid()
});

这将生成一个“真实”的Guid值。当您新建引用类型时,它将为您提供默认值(在这种情况下,对于Guid而言,全为零)。

创建新的Guid时,它将初始化为全零,这是Guid的默认值。基本上与创建“新” int(这是一个值类型,但是您仍然可以这样做)相同:

Guid g1;                    // g1 is 00000000-0000-0000-0000-000000000000
Guid g2 = new Guid();       // g2 is 00000000-0000-0000-0000-000000000000
Guid g3 = default(Guid);    // g3 is 00000000-0000-0000-0000-000000000000
Guid g4 = Guid.NewGuid();   // g4 is not all zeroes

将此与使用int做相同的事情进行比较:

int i1;                     // i1 is 0
int i2 = new int();         // i2 is 0
int i3 = default(int);      // i3 is 0

1
g1将仅编译为字段,而不编译为局部变量。另外,您的注释列中的索引与代码的同一行不匹配
CodesInChaos 2011年

1
@CodeInChaos:谢谢,修复了评论。仅供参考,g1行实际上可以编译...
JohnD

3
它将按原样编译,但没有定义的值。如果您添加了读取它的代码(在写入之前),它将不再编译。
CodesInChaos 2011年

1
正确的一点是,如果使用未初始化的变量,则会出现错误,因此无法使用该值。
JOHND

1
投票失败,因为“ Guid = Guid.NewGuid();”行 可能会使新开发者感到困惑。考虑编辑类似“ Guid someGuid = Guid.NewGuid();”的内容 像g2线一样;)
daviesdoesit


19

无法告诉您这已经捕获了多少次。我。

Guid myGuid = Guid.NewGuid(); 

11

本着完整的精神,指导您使用的答案Guid.NewGuid()是正确的。

解决后续的修改时,您需要发布RequestObject课程代码。我怀疑您的guid属性未标记为DataMember,因此无法通过网络进行序列化。由于default(Guid)new Guid()(即,所有0)相同,因此可以解释您所看到的行为。

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.