C# 如何将一系列if语句转换为for或foreach循环?

C# 如何将一系列if语句转换为for或foreach循环?,c#,C#,我在学C#是为了上一门课。我目前的任务是建立一个健身房会员表。我有它的工作,但我一直认为必须有一个更好的方式来完成我的一项职能 我有一份健身房额外活动清单: 24/7访问 饮食咨询 租金 PT 每个都有一个关联的值。如果检查了饮食,那么20美元将添加到基本会员等。目前,我将其设置为如下(有效): 有人能帮我理解如何将其转换为for循环或foreach循环吗?我一直在寻找;我试着将其作为一个数组,但对需要添加的值感到困惑,等等 按下“计算”按钮后,输出将进入表单上的文本框。这里最简单的做法是引

我在学C#是为了上一门课。我目前的任务是建立一个健身房会员表。我有它的工作,但我一直认为必须有一个更好的方式来完成我的一项职能

我有一份健身房额外活动清单:

  • 24/7访问
  • 饮食咨询
  • 租金
  • PT
每个都有一个关联的值。如果检查了饮食,那么20美元将添加到基本会员等。目前,我将其设置为如下(有效):

有人能帮我理解如何将其转换为for循环或foreach循环吗?我一直在寻找;我试着将其作为一个数组,但对需要添加的值感到困惑,等等


按下“计算”按钮后,输出将进入表单上的文本框。

这里最简单的做法是引入一个可枚举(列表、数组等)来捕获您的复选框和额外成本:

var checks = new []
{
    new { CheckBox = accessCheck, ExtraCost = 1, },
    new { CheckBox = personalTrainerCheck, ExtraCost = 20, },
    new { CheckBox = dietConsultCheck, ExtraCost = 20, },
    new { CheckBox = fitnessVidCheck, ExtraCost = 2, },
};
现在很容易将额外成本加起来:

var extraCost = 0;
foreach (var check in checks)
{
    if (check.CheckBox.Checked)
    {
        extraCost += check.ExtraCost;
    }
}
return extraCost;
现在,如果你想让它更精简一点,那么你可以用这个来代替这个计算:

return checks.Aggregate(0, (a, x) => x.CheckBox.Checked ? x.ExtraCost : 0);
接下来出现的问题是,情况变得更加复杂,如
healthCheck.Checked&&dietConsultCheck.Checked
location==“CBD”&&fitnessVidCheck.Checked
。然后,您可以执行以下操作:

var checks = new (Func<bool> Condition, int ExtraCost)[]
{
    (() => accessCheck.Checked, 1),
    (() => personalTrainerCheck.Checked, 20),
    (() => healthCheck.Checked && dietConsultCheck.Checked, 20),
    (() => location == "CBD" && fitnessVidCheck.Checked, 1),
};
return checks.Aggregate(0, (a, x) => x.Condition() ? x.ExtraCost : 0);
然后,在启动时,您可以设置默认值:

_checks = new List<(Func<bool> Condition, int ExtraCost)>()
{
    (() => accessCheck.Checked, 1),
    (() => personalTrainerCheck.Checked, 20),
    (() => healthCheck.Checked && dietConsultCheck.Checked, 20),
    (() => location == "CBD" && fitnessVidCheck.Checked, 1),
};

另一个例子是,使用一个专门的类对象来处理(或者可以很容易地修改)与选择这些复选框相关的所有操作


类对象是使用
IEnumarable((复选框,十进制))
构建的,并创建一个
字典。您拥有的代码没有问题,尽管如果有更多复选框,可能会有点冗长。您可以将复选框实例添加到
字典
列表
,在表单构造之后,您可以遍历该列表以检查
选中的
和值等。另一种方法是将成本存储在CheckBox标记中,并遍历表单上的所有复选框,尽管老实说,这并不是最好的方法,而且很难实现maintain@MichaelRandall-我打算用
列表
做一个回答。既然你先有了这个想法,你想吗?@Engmativity更重要的是谁先发布答案作为答案。这里的两个人似乎都有足够的网站经验,知道如何更好地将答案作为评论发布。我认为像你这样使用
if
',可以使代码简单易读。我会留着的。嗨,吉米,非常感谢你。我不得不说,这对我现在的处境来说有点过头了,但我肯定会研究这一点,并将其作为一种学习工具。我真的很感谢你花时间回答这个问题并制作这个展示。我想其他人也会从你的回答中受益匪浅。再次感谢!当然,没问题。这是一种有点经典的方法,当您必须处理执行相同操作的数量不确定的控件并自动执行此操作时,它会派上用场。如果需要添加另一个控件,则在创建处理程序(此处为ExtraServices类)时向集合添加新元素。没有其他需要。表单、控制器或演示者中没有其他代码。我看到《谜》在概念上发布了一些相对类似的东西。尝试使用这些方法,而不是在代码中添加大量的
if/elseif
块,然后您必须手动管理这些块。
private List<(Func<bool> Condition, int ExtraCost)> _checks = null;
_checks = new List<(Func<bool> Condition, int ExtraCost)>()
{
    (() => accessCheck.Checked, 1),
    (() => personalTrainerCheck.Checked, 20),
    (() => healthCheck.Checked && dietConsultCheck.Checked, 20),
    (() => location == "CBD" && fitnessVidCheck.Checked, 1),
};
_checks.Add((() => monthlySpecialCheck.Checked, -10));
private class ExtraServices
{
    private Dictionary<CheckBox, Func<decimal>> services = null;
    public ExtraServices(IEnumerable<(CheckBox uiElement, decimal assocPrice)> servicePrices)
    {
        services = new Dictionary<CheckBox, Func<decimal>>();
        foreach (var service in servicePrices) {
            services.Add(service.uiElement, ()=>
                AddVAT ? service.assocPrice + (service.assocPrice * VAT / 100) 
                       : service.assocPrice
            );
        }
    }

    public decimal VAT { get; set; } = 10.00M;
    public bool AddVAT { get; set; } = false;

    public decimal GetSelectedServicesExtras()
    {
        return services.Aggregate(0.0M, (sum, elm) => 
            sum += elm.Key.Checked ? elm.Value() : 0M);
    }
}
private ExtraServices extras = null;
private decimal extrasTotal = 0.0m;

protected override void OnLoad(EventArgs e)
{
    base.OnLoad(e);

    extras = new ExtraServices(new[] {
        (chkAccess, 1.0m),
        (chkPersonalTrainer, 20.0m),
        (chkDietConsult, 20.0m),
        (chkFitnessVid, 2.0m),
    }) { AddVAT = false };

    // Sets the initial values to 0.0m and formats the output
    CalculateExtras();
}
private void chkExtras_CheckedChanged(object sender, EventArgs e)
{
    CalculateExtras();
}

private void chkAddVAT_CheckedChanged(object sender, EventArgs e)
{
    extras.AddVAT = (sender as CheckBox).Checked;
    CalculateExtras();
}

private void CalculateExtras()
{
    extrasTotal = extras.GetSelectedServicesExtras();
    txtExtrasTotal.Text = extrasTotal.ToString("C");
}