【问题标题】:C# - pass on expanded params array to another functionC# - 将扩展的参数数组传递给另一个函数
【发布时间】:2020-11-01 16:52:00
【问题描述】:

params 数组传递给另一个函数时如何扩展它。

考虑以下示例:

public class TestClass
{
    public static void Main()
    {
        TestParamFunc(1, "1", 1.0f, 1.0);

        Console.ReadKey();
    }

    private static void TestParamFunc(params object[] parameters)
    {
        //At the moment the DeeperTestParamFunc receives the following parameters: { int, object[] }
        //How to expand this to { int, int, string, float, double } ?
        //So that { 1, 1, "1", 1.0f, 1.0 } is received.
        DeeperTestParamFunc(1, parameters);
    }

    public static void DeeperTestParamFunc(params object[] parameters)
    {
        foreach(object obj in parameters)
        {
            Console.WriteLine(obj.GetType().ToString());
        }
    }
}

输出:

System.Int32
System.Object[]

我想要的输出:

System.Int32
System.Int32
System.String
System.Single
System.Double

【问题讨论】:

    标签: c# arrays parameters expand


    【解决方案1】:

    您创建一个新数组,将现有参数复制到其中,添加更多内容并使用更大的数组调用另一个方法

    说到底,这些只是数组。 params 只是意味着编译器允许你单独指定参数,它会为你把它变成一个数组

    你写这个:

    MyFuncWithParamsObjectArg(1,2,3,4,5);
    

    编译器在概念上将其更改为:

    MyFuncWithParamsObjectArg(new object [] {1,2,3,4,5} );
    

    这是一个演示程序:

    public static void Main()
    {
        A("z", "y");
        
    }
    
    static void A(params object[] a){
        Console.WriteLine("In A()");
        
        foreach(object o in a)
            Console.WriteLine(o);
        
        object[] oo = new object[a.Length + 2];
        
        for(int i = 0; i < a.Length; i++)
            oo[i] = a[i];
        
        oo[a.Length] = "new";
        oo[a.Length + 1] = "new2";
        
        B(oo);
    }
    
    static void B(params object[] b){
        Console.WriteLine("In B()");
        
        foreach(object o in b)
            Console.WriteLine(o);
    }
    

    打印出来:

    In A()
    z
    y
    In B()
    z
    y
    new
    new2
    

    你可以看到 B 被调用了一个比 a 长 2 的数组,并且增加了两个元素

    注意,你不能“扩展”一个数组,不管它是否是参数。您必须创建一个新数组,将内容复制过来,然后从那里开始

    如果您希望将其包装起来,这样您就不会展平第一个数组,而是制作另一个将第一个数组作为其元素之一的 params 数组:

    static void A(params object[] a){
        Console.WriteLine("In A()");
        
        foreach(object o in a)
            Console.WriteLine(o);
        
        B(a, "new1", "new2");
    }
    

    B 现在将得到一个如下所示的数组:

    object[] {
       object[] { "z", "y" },
       "new1",
       "new2"
    }
    

    如前所述;没有魔法 - 编译器会查看您提供的内容,如果参数与“使用单维数组调用”匹配,那么它会使用数组调用函数,否则它会收集各种参数,将它们转换为数组,然后调用它与那个数组

    B(a);                                  //a is already an object array, it is passed in verbatim
    B(a, "new1", "new2");                  //a new object array is created from these 3 objects
    B(new object[] {a, "new1", "new2"} );  //manually doing what the compiler does for you above
    

    【讨论】:

    • 感谢您的详细解答!对于那些感兴趣的人,这是我所做的: DeeperTestParamFunc(parameters.Prepend(5).ToArray());
    • 是的,这确实采用了准备新数组的 LINQ 路线。它不需要使用 params 函数 - 请参阅我的答案中的后一个编辑以了解原因
    【解决方案2】:

    这就是你想要的:

        private static void TestParamFunc(params object[] parameters)
        {
            // manually create the array in the form you need
            var deeperParameters = new object[parameters.Length + 1];
            deeperParameters[0] = 1;
            parameters.CopyTo(deeperParameters, 1);            
            DeeperTestParamFunc(deeperParameters);
        }
    

    【讨论】:

      【解决方案3】:

      试试:

      public static void DeeperTestParamFunc(params object[] parameters)
              {
                  foreach (object obj in (IEnumerable) parameters[1])
                  {
                      Console.WriteLine(obj.GetType().ToString());
                  }
              }
      

      实例:

      public static void DeeperTestParamFunc(params object[] parameters)
          {
              foreach(object obj in parameters)
              {
                  Console.WriteLine(obj.GetType().ToString());
              }
          }
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2012-09-25
        • 2020-10-03
        • 1970-01-01
        • 1970-01-01
        • 2018-07-16
        • 2014-01-06
        相关资源
        最近更新 更多