C# 在控件标记属性中存储对象引用是否正常

C# 在控件标记属性中存储对象引用是否正常,c#,winforms,object,C#,Winforms,Object,我正在为列表中的每个对象创建一组表单控件,是否可以在控件标记属性中存储对该对象的引用 我这样做是为了在控件上有一个通用的单击事件,这样当它们被单击时,我可以更新它们所表示的对象中的一个字段 因此,单击处理程序将如下所示 private void Item_Clicked(object sender, system.EventArgs e) { if(sender.GetType() == typeof(System.Windows.Forms.Label)) {

我正在为列表中的每个对象创建一组表单控件,是否可以在控件标记属性中存储对该对象的引用

我这样做是为了在控件上有一个通用的单击事件,这样当它们被单击时,我可以更新它们所表示的对象中的一个字段

因此,单击处理程序将如下所示

private void Item_Clicked(object sender, system.EventArgs e)
{
     if(sender.GetType() == typeof(System.Windows.Forms.Label))
     {
          System.Windows.Forms.Label label = (System.Windows.Forms.Label)sender;
          MyObject myObject = label.Tag;
          myObject.Value = true;
     }
}

在这种情况下,这样做是可以接受的,还是有更好的方法来处理这个问题?

是的,这样做是合法的,并且是
标记
属性设计的模式之一

这里最大的危险是,另一批代码试图将相同的
标记
属性用于自己的功能。这将为
标记
属性创建竞争,并导致运行时错误。更安全的方法是使用
字典
实例在
标签
MyObject
之间创建私有映射

private Dictionary<Label,MyObject> _map = new Dictionary<Label,MyObject>();
...
private void Item_Clicked(object sender, system.EventArgs e) 
{ 
     if(sender.GetType() == typeof(System.Windows.Forms.Label)) 
     { 
          System.Windows.Forms.Label label = (System.Windows.Forms.Label)sender;
          MyObject myObject = _map[label];
          myObject.Value = true; 
     } 
}
private Dictionary\u map=new Dictionary();
...
已单击私有无效项(对象发送者,system.EventArgs e)
{ 
if(sender.GetType()==typeof(System.Windows.Forms.Label))
{ 
System.Windows.Forms.Label Label=(System.Windows.Forms.Label)发件人;
MyObject MyObject=_映射[标签];
myObject.Value=true;
} 
}

这种方法具有
字典的额外开销,但会产生更可靠的代码(IMHO)。

是的,这样做是合法的,并且是
标记
属性设计的模式之一

这里最大的危险是,另一批代码试图将相同的
标记
属性用于自己的功能。这将为
标记
属性创建竞争,并导致运行时错误。更安全的方法是使用
字典
实例在
标签
MyObject
之间创建私有映射

private Dictionary<Label,MyObject> _map = new Dictionary<Label,MyObject>();
...
private void Item_Clicked(object sender, system.EventArgs e) 
{ 
     if(sender.GetType() == typeof(System.Windows.Forms.Label)) 
     { 
          System.Windows.Forms.Label label = (System.Windows.Forms.Label)sender;
          MyObject myObject = _map[label];
          myObject.Value = true; 
     } 
}
private Dictionary\u map=new Dictionary();
...
已单击私有无效项(对象发送者,system.EventArgs e)
{ 
if(sender.GetType()==typeof(System.Windows.Forms.Label))
{ 
System.Windows.Forms.Label Label=(System.Windows.Forms.Label)发件人;
MyObject MyObject=_映射[标签];
myObject.Value=true;
} 
}

这种方法具有
字典的额外开销,但会产生更可靠的代码(IMHO)。

如果它适合您,则是可以接受的。我以前已经像这样将东西正确地存储在标签中,而且效果很好。需要考虑的事项:您存储的对象的大小和对象的生命周期(在访问之间是否可以处理或销毁)


我使用的另一种方法是存储一个“提示”,帮助您检索或重新创建对象。例如,如果它是一个数据库对象,则存储Id属性(可能是整数或Guid),该属性[可能]比对象本身小得多。

如果它适合您,则可以接受。我以前已经像这样将东西正确地存储在标签中,而且效果很好。需要考虑的事项:您存储的对象的大小和对象的生命周期(在访问之间是否可以处理或销毁)


我使用的另一种方法是存储一个“提示”,帮助您检索或重新创建对象。例如,如果它是一个数据库对象,则存储Id属性(可能是一个整数或Guid),该属性[可能]比对象本身小得多。

如果我只使用标签,这种方法就可以工作。我的例子是我正在做的一个简短版本。实际上,我有一些if语句来确定单击了哪种类型的控件。在我的例子中,我应该创建一个类似于此字典的字典吗?@Tester101是的,如果您需要将控件(而不仅仅是示例中的标签)映射到MyObject,那么这将起作用。我认为,如果两个或多个线程修改一个字典,您会遇到与Tag属性相同的问题。。只有阅读仍然是一个可行的解决方案,但是你也可以使用属性标签,对吗?如果我只使用标签,这种方法就行了。我的例子是我正在做的一个简短版本。实际上,我有一些if语句来确定单击了哪种类型的控件。在我的例子中,我应该创建一个类似于此字典的字典吗?@Tester101是的,如果您需要将控件(而不仅仅是示例中的标签)映射到MyObject,那么这将起作用。我认为,如果两个或多个线程修改一个字典,您会遇到与Tag属性相同的问题。。只有阅读仍然是一个可行的解决方案,但是你也可以使用属性标签,对吗?