C# 正确使用特性以嵌套形式维护HUD? 编辑1

C# 正确使用特性以嵌套形式维护HUD? 编辑1,c#,winforms,oop,properties,C#,Winforms,Oop,Properties,是否可以使用get/set执行此操作?像下面这样的?这对我来说很有效,但我担心我遗漏了一些东西,更不用说所有的静态了 现在,当我从注册页面调用它时,我希望所有内容都保留下来并添加注册ID private void GetResults() { var enrollmentID = getCurrentRowVal("EnrollmentID"); HUD.UpdateHUD(FrmWwcModuleHost, enrollmentID);

是否可以使用get/set执行此操作?像下面这样的?这对我来说很有效,但我担心我遗漏了一些东西,更不用说所有的静态了

现在,当我从注册页面调用它时,我希望所有内容都保留下来并添加注册ID

        private void GetResults()
    {
        var enrollmentID = getCurrentRowVal("EnrollmentID");

        HUD.UpdateHUD(FrmWwcModuleHost, enrollmentID);
    }
我的问题是,如何做到这一点,并知道调用哪个arg[]索引,而不覆盖现有值

它是否像总是提供设置的所有参数一样简单?因此,我在注册页面上的呼叫将改为如下-->


谢谢你的见解

我要做的是使用ananoymous类型(可以在运行时转换为字典),然后更改存在的值

新功能定义:

public static void UpdateHUD (FrmModuleHost frm, object args);
和客户端代码:

UpdateHUD(frm, new {
    MiddleName = "Jed",
    SSN = "..." });
使用中的代码,可以将其转换为字典。新的实施类似于:

var dictionary = MakeDictionary(args);
if ( dictionary.ContainsKey("SSN") ) { _sSN = dictionary["SSN"]; }

当然,当C#4.0问世时,这一切都无关紧要。

您确实需要放弃params样式调用,为您的方法建立真正的参数。只需为最常见的调用签名创建多个重载。

C#4.0具有可选参数,这些参数与params关键字有很大不同。Params关键字在运行时与根本没有Params关键字的情况没有什么不同。换句话说,你只是得到一个值数组,无法知道哪些是哪些。Params关键字在编译时只是一种方便

尽管我还没有使用C#4.0可选参数,但我认为它们的行为与VB.NET可选参数的行为类似,因为您可以在函数中指定默认值,如果调用方没有指定默认值,将使用默认值。但是调用者仍然必须指出(缺少值或paramName:=语法)他们正在指定的参数

在您的情况下,我认为最好使用普通命名参数并在不需要时传递null,或者传递字典/哈希表。

也许可以代替

params String[] args
你应该这样做

params KeyValuePair<String,String>[] args

然后在
UpdateHUD
方法中,您可以检查参数的
键是什么,这样您就可以知道传递的是哪个值。

您可以通过字典传递参数,在字典中可以为某个名称赋值

最干净的版本是为每个变量创建一个方法。 e、 g


如果可以使用Framework4.0,则可以使用。在此之前,您需要传递所有参数


但是,我认为你的问题可能会误解正在发生的事情。您在params中发送的参数将作为参数进入方法。因此,它们的范围是方法本身,因此您不会“覆盖”任何内容。用于第一次调用的数组已消失(超出范围),用于第二次调用的数组将包含您放入其中的任何内容。在4.0之前执行可选参数的最佳方法是使用多个方法重载。

您还可以创建一个单独的类以在params数组中传递。比如:

public class HUDParam {
   public HUDParam(paramName, paramValue) { /*[init code here...]*/ }
   public string Name { get; set; }
   public string Value { get; set; }
}
然后:


在更新方法中,您只需检查名称并在HUD中设置适当的值。

如果名称与值关联,但名称值可能未知,则这是字典的候选项


可选参数所涉及的检查不亚于检查字典中是否存在键或类的成员是否为null。因为已经存在一个用于此的原语,而且它更灵活,所以我认为没有理由使用可变参数或可选参数。

我没有看到对您正在使用的.net特定版本的引用。下面是我在.NET3.5中处理这个问题的方法

首先创建一个类来传递更新值,但要使所有属性都可以为null(因为所有项都是字符串,所以它们已经可以为null)。如果值可为空,请添加实际的属性设置器和LastNameChanged属性

 public class UpdateData {
    public string LastName { get; set;};
    public string FirstName  { get; set;};
    public string MiddleName  { get; set;};
 ...
 }
现在,您的方法签名如下所示:

Key = "Last Name"
Value = "Hare"
public static void UpdateHUD (FrmModuleHost frm, UpdateData  data)
{
    if (!string.IsNullOrEmpty(data.FirstName) {
    frm.tbxHUD_LastName.Text = data.FirstName;
    _lastName = data.FirstName;
    }

    if (!string.IsNullOrEmpty(data.LastName) {
    frm.tbxHUD_FirstName.Text = data.LastName;
    _firstName = data.FirstName;
    }
    if (!string.IsNullOrEmpty(data.MiddleName) {
    frm.tbxHUD_MiddleName.Text = data.MiddleName;
    _middleName = data.FirstName;
    }
接下来是设置UpdateData并调用该方法:

UpdateHUD(FrmWwcModuleHost, new UpateData{ FirstName = "test1", LastName = "test2", ...});

最后一点注意:这里使用了大量的静力学。你可以考虑改变其中的大部分。将静态变量移动到具有属性(但没有静态)的实际类,并在代码中引用该类。

您的代码要求在params部分中只传递四个参数。如果要求参数数组始终为4,那么首先为什么要使用参数数组?param数组的用途是可以传递任意数量的参数,例如,名称列表。为什么不简单地说publicstaticvoidupdatehud(FrmModuleHost frm,stringlast,stringfirst,stringmiddle,stringid)?因为中间名可能不知道。并非所有类型的成员都需要SSN。与注册和计划ID相同。唯一可以硬编码的字段是名字和姓氏。然后对支持的每个组合进行不同的重载。我希望这是一个单用户、单线程的应用程序。所有那些在没有任何锁定的情况下修改静态变量的做法都让我感到不安。确实如此,尽管我正在试图弄清楚如何在这里使用OOP。似乎我需要将我的对象传递给每个表单。-1这将需要反射来运行类型,然后需要更多管道来访问每个成员。4在这一点上不是一个选项。关于你的第二点;如果我传入Null,我不会丢失现有信息吗?例如,当我传入注册ID时的名字?那么在我的HUD中每个字段都有一个方法吗?这可能是可行的,因为只有9个。
void UpdateLastName(string name)
{
   frm.tbxHUD_LastName.Text = _lastName = name;
}
public class HUDParam {
   public HUDParam(paramName, paramValue) { /*[init code here...]*/ }
   public string Name { get; set; }
   public string Value { get; set; }
}
HUD.UpdateHUD(frm, new HUDParam("FirstName", "Tom"), 
    new HUDParam("LastName", "Thompson");
 public class UpdateData {
    public string LastName { get; set;};
    public string FirstName  { get; set;};
    public string MiddleName  { get; set;};
 ...
 }
public static void UpdateHUD (FrmModuleHost frm, UpdateData  data)
{
    if (!string.IsNullOrEmpty(data.FirstName) {
    frm.tbxHUD_LastName.Text = data.FirstName;
    _lastName = data.FirstName;
    }

    if (!string.IsNullOrEmpty(data.LastName) {
    frm.tbxHUD_FirstName.Text = data.LastName;
    _firstName = data.FirstName;
    }
    if (!string.IsNullOrEmpty(data.MiddleName) {
    frm.tbxHUD_MiddleName.Text = data.MiddleName;
    _middleName = data.FirstName;
    }
UpdateHUD(FrmWwcModuleHost, new UpateData{ FirstName = "test1", LastName = "test2", ...});