我有一个像这样定义的属性ggFileName:
private string _ggFileName = "";
public string ggFileName
{
get
{
return _ggFileName;
}
set
{
_ggFileName = value;
ReadXmlSchemaFromFile();
}
}
当为ggFileName赋值时,方法ReadXmlSchemaFromFile();叫做。 到目前为止一切都很好。
我的问题是,当我为属性ggFileName分配它已经包含的相同值时,没有任何反应。在我为其分配不同的值之前,不会调用setter。
我同意在几乎所有情况下这都是完全合乎逻辑的,但在我的情况下它会引发一个问题。 如果ggFileName中的文件在我的应用程序之外更改怎么办? 将同一文件再次分配给ggFileName不会调用我的setter,因此也不会调用ReadXmlSchemaFromFile()。所以现在我必须将一个虚拟文件设置为属性ggFileName,然后再将同一文件分配给ggFileName以使其正常工作。
C#似乎想通过在分配相同值时不调用setter来帮助我,我怎么能告诉c#停止帮助我呢?
我不知道c#这样做了,在我的所有安装程序中我都有这样的代码: if(value!= _myValue){do setter logic here} 我想我不需要写那个支票了吗?
只是为了让事情更清楚,因为人们似乎不理解我的问题。 1.我的setter确实被调用,但只有在分配不同的值时才会被调用 2.我不想使用方法,因为在设置属性之后我想要完成一些检查,并且我不希望我班级的任何其他用户能够绕过该检查。属性的用途是什么? 3.分配我无法发布的值的代码。它是自定义控件的属性,设计者通过编辑对象检查器来调用它。同样,只要我继续为它提供不同的值,它就会起作用
感谢
答案 0 :(得分:17)
对于它的价值 - 我遇到了这个问题,在我们的代码库中它已经达到了Fody。
Fody插入相等检查并使设定器短路。我并没有真正期待你的问题归结为Fody(因为你提到了视觉设计师)。我认为对我这样做的人来说,这可能是有价值的。
我使用dotPeek来查找要插入的代码。
为了您的利益,我使用dotPeek检查winforms PropertyGrid并找到下面的代码片段。视觉工作室可能会有所不同,但我强烈怀疑它正在做类似的事情。如果您非常热衷于在设置不同值时可以记录调用堆栈。调用堆栈中的某个位置是具有相等性检查的函数。
private object SetPropertyValue(object obj, object objVal, bool reset, string undoText)
{
DesignerTransaction designerTransaction = (DesignerTransaction) null;
try
{
object propertyValueCore = this.GetPropertyValueCore(obj);
if (objVal != null && objVal.Equals(propertyValueCore)) // if equal return!!!!
return objVal;
this.ClearCachedValues();
关于Fody:
这种"编织"在新的指示是奇妙的 强大。您可以将简单的公共属性变为完整 INotifyPropertyChanged实现,添加对空参数的检查, 将Git哈希添加到您的程序集中,甚至可以创建所有字符串 比较不区分大小。
值得注意的是,可以使用[DoNotCheckEquality]禁用它。
答案 1 :(得分:3)
问题在于视觉工作室的有缺陷的设计师。 在设计时使用“属性窗口”设置属性值时,如果属性值已经存在,则此窗口不会设置该属性的值。
在代码中执行此操作时没有任何问题,无论如何都将设置该值。
这是微软试图帮助你的另一个很好的例子(所有这些都可以帮助你倒退而不是前锋......)
答案 2 :(得分:0)
我今天在properyGrid中使用文件名属性遇到了同样的问题。
我发现一个简单的变通办法是零星的,但这对我有好处。我没有在getter中返回_ggFileName
,而是返回了“浏览文件”
我确保不使用吸气剂,而是使用字段
因此,基本上唯一使用吸气剂的是属性网格,这当然不是很好的编程方法,但是它很快就为我解决了这个问题。
private string _ggFileName = "";
public string ggFileName
{
get
{
return "Browze File";
}
set
{
_ggFileName = value;
ReadXmlSchemaFromFile();
}
}