简体   繁体   English

在 C# 中以编程方式构建参数列表

[英]Building parameter list programmatically in C#

*Say I've got a class with a constructor with one required parameter and three optional ones. *假设我有一个 class 带有一个带有一个必需参数和三个可选参数的构造函数。

public class myClass(int reqInt, string optStr1 = "st1", uint optUint1 = 0, float optFloat =0.0)
{ ... }

I know that, in my calling code, I can effectively treat this as an overloaded function, eg我知道,在我的调用代码中,我可以有效地将其视为重载的 function,例如

myClass Foo = new myClass(1, "test");
myClass Foo2 = new myClass(2, "hellow world", 4);

and even乃至

myClass Foo3 = new myClass(3, optFloat : 4.5)

What I can't figure out is how to build my parameters tuple dynamically.我想不通的是如何动态构建我的参数元组。 Eg say my data is coming from a JSON, and I might get the following array:例如,假设我的数据来自 JSON,我可能会得到以下数组:

[
 { "myInt" : "1"}, 
 {"myInt :"2", "myString" : "word"}, 
 {"myFloat" : "4.5", "myString" : "to" , "myInt" : "3"}, 
 {"myUInt" : "4", "myInt" "-4", "myFloat" : "4.4", "myString" : "yo!"}
]

I can obviously create 8 different callers*, but that seems like it just moves the overload from the constructor to the caller.我显然可以创建 8 个不同的调用者*,但这似乎只是将重载从构造函数转移到调用者。 But I can't figure out how to dynamically build the tuple, especially using named parameters/aliases, so I only have 1 calling function.但我不知道如何动态构建元组,尤其是使用命名参数/别名,所以我只有 1 个调用 function。

An arraylist seems like it would work, but (I think) I need to use named parameters, since there will be cases where I don't have optional parameter 1, but do have 2 or 3 (or any combinations thereof). arraylist 似乎可以工作,但是(我认为)我需要使用命名参数,因为在某些情况下我没有可选参数 1,但确实有 2 或 3(或其任何组合)。

This can't be an edge case, but I'm not finding anything that works in my searches (I don't work in C#, or really any strongly typed languages most of the time, so forgive me if this is a really basic question).这不可能是边缘情况,但我没有找到任何在我的搜索中有效的东西(我大部分时间不在 C# 或任何强类型语言中工作,所以如果这是一个非常基本的语言,请原谅我问题)。

*meaning, assume I've deserialized my Json into myJson , I could do: *意思是,假设我已经将我的 Json 反序列化为myJson ,我可以这样做:

If(myJson.myString.hasValue){
   if(myJson.myString.hasValue){
      if(myJson.myUInt.hasValue){
         if(myJson.myFloat.hasValue){
            (int, string, uint, float) myParams = (reqint: myJson.myInt, optStr1: myJson.myString, optUint1: myJson.myUInt, optFloat: myJson.myFloat)
         } else if
...

and so on, recursively building up the 8 possible cases.依此类推,递归地构建 8 种可能的情况。 But that seems really verbose...但这似乎真的很冗长......

You could use a builder您可以使用构建器

Given给定

public class MyClassBuilder
{
   public int reqInt { get; set; }
   public string optStr1 { get; set; } = "st1";
   public uint optUint1 { get; set; }
   public float optFloat { get; set; }
}

Example例子

public class MyClass
{
   public MyClass(MyClassBuilder builder) 
     : this(builder.reqInt, builder.optStr1, builder.optUint1, builder.optFloat)
   {

   }
   public MyClass(int reqInt, string optStr1 = "st1", uint optUint1 = 0, float optFloat = 0.0f)
   {

   }
}

Usage用法

// Once you have deserialized to your builder, or set it somehow

var myClass = new MyClass(builder);

If your constructor options are more complicated than this, you will have to use branching in your constructor and fill out the fields manually.如果您的构造函数选项比这更复杂,您将不得不在构造函数中使用分支并手动填写字段。

Another way to achieve this, is just deserialize MyClass the way it is.实现此目的的另一种方法是按原样反序列化 MyClass。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM