【问题标题】:How To create unknown-multidimensional parameter?如何创建未知多维参数?
【发布时间】:2020-07-23 11:40:08
【问题描述】:

我想知道是否可以创建一个通用的多维参数。我正在制作一个通用列表/数组洗牌类,它将有一个静态方法,该方法获取一个 IEnumerable 参数并返回相同但已经洗牌。问题是我不知道如何使参数如此通用以至于它可以获得任意数量的维度数组/列表。

提前谢谢你。

这是我现在写的代码:

 public static IEnumerable<T> OneDimensionalShuffle<T>(IEnumerable<T> array)
    {
        var originalList = array.ToList();
        var shuffledList = new List<T>();

        var rand = new Random();

        for (var i = originalList.Count - 1; i >= 0; i--)
        {
            var randomArrayPosition = rand.Next(i + 1); //i+1 because maxValue is exclusive
            shuffledList.Add(originalList[randomArrayPosition]); //Add random point to the shuffledList
            originalList.RemoveAt(randomArrayPosition); //Remove element which was already added to shuffledList
        }

        array = shuffledList;
        return array;
    }

【问题讨论】:

  • 能否请您出示有关此事的当前代码?用它来指导您找到具体的解决方案会更容易。
  • 您可以使用 IEnumerable 数组:IEnumerable[]

标签: c# generics methods shuffle generic-method


【解决方案1】:

据我所知,没有办法访问任意等级的通用类型多维数组。

备选方案 1:使用无类型数组

Array arr = new int[1,1];
var rank = arr.Rank;
var value = arr.GetValue(0,0);

这样做的缺点是速度很慢,并且会导致一堆拳击。

备选方案 2:使用自定义多维类型

 public class MyMultiDimensionalArray<T>{
      public T[] backingDataStorage {get;}
      public int Rank {get;}
      public int[] Length {get;}
      public T GetValue(params int[] indices){
           // Math to convert the indices to a one dimensional value
      }
 }

这样做的一个优点是您可以使用泛型类型,并允许直接访问底层数组。缺点是您需要编写一堆数学来将任意等级的索引转换为一维索引。它的一个变体是具有不同的类型,My2DArray、My3DArray 等,以及一个通用接口。

备选方案 3:根据需要定义尽可能多的方法

 public static void MyMethod<T>(T[]) { /*...*/}
 public static void MyMethod<T>(T[,]) { /*...*/}
 public static void MyMethod<T>(T[,,]) { /*...*/}
 public static void MyMethod<T>(T[,,,]) { /*...*/}

这很容易做到并允许通用类型,但需要大量重复代码。

根据我的经验,1d、2d 和 3d 数组是最常见的。我从未见过在野外使用的 4d 数组。甚至 3d 数组也经常变得如此之大,以至于将一个维度存储为锯齿状数组会更好,即 int[][,],因为它避免了对巨大连续内存块的需要,允许锁定单个切片等。我更喜欢使用自定义的多维数组类型,因为我发现想要对数据进行线性访问是很常见的,比如序列化或洗牌。

【讨论】:

    猜你喜欢
    • 2019-08-17
    • 1970-01-01
    • 1970-01-01
    • 2011-11-24
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多