【问题标题】:Convert type List<object> to 'T'将类型 List<object> 转换为 \'T\'
【发布时间】:2022-11-02 17:19:47
【问题描述】:

我正在尝试编写一个通用函数:

private T Convert<T>(List<object> list) where T : new()
{
    if (typeof(T).IsArray)
    {
        T array = new T();
        // ... convert here
        return array;
    }
}

在这种情况下,我知道list 中的对象应该与T 的数组类型相同。例如,如果TSystem.Int32[],那么我希望list 中的对象都是Int32

但是,T 并不总是一个数组。在其他情况下,它可能是值类型,甚至是其他一些引用类型。

鉴于这些假设,我如何将 List&lt;object&gt; 转换为 T

更新

这似乎在一组给定的假设范围内起作用:

private T Convert<T>(List<object> list)
{
    // ... code omitted for brevity

    if (typeof(T).IsArray)
    {
        // big assumption here
        Type elementType = Type.GetType(typeof(T).FullName.Replace("[]", string.Empty));

        Array array = Array.CreateInstance(elementType, list.Count);
        for (int i = 0; i < list.Count; i++)
        {
            array.SetValue(list[i], i);
        }
        return (T)Convert.ChangeType(array, typeof(T));
    }
}

【问题讨论】:

  • Linq 已经有 .Cast&lt;T&gt;() 方法,它做同样的事情。
  • 如果列表中的所有对象都是同一类型,那么您可能想要做的是将List&lt;T&gt; 转换为T[]。然后,编译器可以从list 参数的类型推断T 的类型。但是,话又说回来,你可以打电话给.ToArray()
  • ...另外,为什么你的代码中有List&lt;object&gt;? (使用object 有点代码味道:在极少数情况下使用object 作为类型是一种合法的解决方案)。你有什么问题真的试图解决?
  • @Dai 在这种情况下, T 可能是许多不同的事物,并且在此函数的范围之外定义。 List<object> 正在从数据库源提供给此函数。如果 T 是一个值类型,我期望一个值并转换它。但是如果 T 是一个数组,我期望 1..n 值并且需要将它作为提供的 T 返回。
  • 如果 T 是一个 int 数组,我希望结果应该是 List<int[]>,而不是 List<int>。如果 T 是一个 int,我会期望一个 List<int>。

标签: c# reflection


【解决方案1】:

您可以使用古老的ArrayList 创建所需类型的数组。 (这几乎是它唯一有用的东西。)

private T Convert<T>(List<object> list) 
{
    if (typeof(T).IsArray)
    {
        var tmp = new ArrayList(list);
        return (T)(object)tmp.ToArray(typeof(T).GetElementType());
    }
    return (T)list.First(); 
}

Fiddle

注意:您可能应该添加一些错误处理,例如如果调用者指定了一个T,这对列表没有意义。

【讨论】:

  • 不幸的是,这在我的情况下不起作用,因为 T 是在外部定义的,可以是值类型或数组类型。我需要在我的函数中解决这个问题。
  • 不确定我是否跟随。您打算如何将List&lt;object&gt; 转换为值类型?
  • 仅取第一个值。想想 ExecuteScalar()。
  • 我懂了。请参阅我修改后的答案。
猜你喜欢
  • 1970-01-01
  • 2019-02-03
  • 1970-01-01
  • 2017-03-11
  • 2018-11-12
  • 2012-11-15
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多