2009-08-21 14 views
9

List<object>'u dinamik olarak List<string>'a yüklemeye çalışıyorum. Birkaç yol denedim ama bir çözüm bulamıyorum. Bu, sorunu gösteren küçük bir örnektir:Genel Listeler C# dilinde dinamik olarak nasıl yayınlanır?

List<object> listObject = new List<object>(); 
listObject.Add("ITEM 1"); 
listObject.Add("ITEM 2"); 
listObject.Add("ITEM 3"); 

List<string> listString = ¿¿listObject??; 

Şimdiden teşekkürler! LINQ kullanabiliyorsa

+8

o kadar türgüvenli olmadığı için bu, her iki sürümü 4'te mümkün olmayacaktır ya "upcast" veya "mahzun" bir 'Liste ' - bu değişmez, değil covariant veya kontravaryant. Bu arada, koleksiyon co/contravariance ile ilgili her soruya verilen bu yanlış bilgiden bıktım. –

cevap

18

sonra Cast yöntemi gerekenleri yapacağız:

List<string> listString = listObject.ConvertAll(x => (string)x); 

ise: Stan onun cevabını işaret ettiği gibi

List<string> listString = listObject.Cast<string>().ToList(); 

Ayrıca, ConvertAll yöntemi kullanabilirsiniz C# 3 kullanmıyorsanız, bir lambda yerine "eski" delege sözdizimini kullanmanız gerekecektir. Bunun yerine "eski" temsilci sözdizimini kullanmanız gerekecektir:

List<string> listString = 
    listObject.ConvertAll(delegate(object x) { return (string)x; }); 
+0

+1 delegate sytnax'ın doğru kullanımı için +1 –

+1

@nader: LINQ mevcut olmadığında her zaman lambda sözdizimi ne olduğunu hatırlamaya çalışıyorum. – LukeH

+0

+1 iyi puan Luke –

4

.NET 3.5 kullanıyorsanız, bu sayede fazladan bir ToList() yapmak zorunda kalmazsınız. Gelişmiş nesneleri dönüştürmeniz gerekiyorsa kendi dönüştürücünüzü de sağlayabilirsiniz.

List<string> listString = listObject.ConvertAll(x=> x as String); 

LINQ kullanamıyorsanız ben bunu bir adım yapabileceğini sanmıyorum bu

foreach(object item in listObject) 
{ 
    string convertedItem = item as String; 
    if(convertedItem != null) 
     listString.Add(convertedItem); 
} 
+1

Bu, .NET 2.0'da da desteklenir (LINQ olmadan, delgate sözdizimi de güzel değildir). Yine de bir not .Cast 'a inanmıyorum .ToList(), ima ettiğiniz gibi bir "ekstra" liste oluşturacaktır. Sonuç olarak, yeni bir liste oluşturacak, yaklaşımınız –

+0

gibi, C# 3.0 ve .Net 3.5 demek istiyorsunuz. – user7116

+0

demek istediğim bu. Teşekkürler. –

0

yapabilirsiniz.

 List<object> listObject = new List<object>(); 
     listObject.Add("ITEM 1"); 
     listObject.Add("ITEM 2"); 
     listObject.Add("ITEM 3"); 

     List<string> lstStr = new List<string>(listObject.Count); 

     foreach (object obj in listObject) 
     { 
      lstStr.Add(obj.ToString()); 
     } 
+0

bu yanlıştır, ToS nesnesindeki tüm ToString() öğelerini istemez, bir string nesnesine dönüştürmek ister. Teknik olarak, örneğiniz bu sefer, ancak sadece dizeler için çalışacaktır. Fakat eğer daha gelişmiş bir nesneye çarpıyorsa, bu yöntemi kullanamaz. –

+0

Tek adımda yapılabilir, diğer yanıtlara bakın ... –

0
List<string> listString = (from o in listObject select (string)o).ToList(); 
+1

Bkz. "Enumerable.Cast ()'. –

1

Şuna ne dersin:

public static List<T> ConvertToGenericList<T>(IList listOfObjects) 
{ 
    List<T> items = new List<T>(); 

    for (int i = 0; i < listOfObjects.Count; i++) 
    { 
     items.Add((T)listOfObjects[i]); 
    } 
    return items; 
} 

Kullanımı:

List<object> listObject = new List<object>(); 
listObject.Add("ITEM 1"); 
listObject.Add("ITEM 2"); 
listObject.Add("ITEM 3"); 
List<string> listString = Converter.ConvertToGenericList<string>(listObject); 
-2

Benim ilk mesaj ... Umut yararlı işler projemde bakar Bunun yerine, böyle bir şey denemek ...

 public dynamic ConvertList(Type CallingType) 
    { 

     dynamic DynamicList; 

     if (CallingType == TypeOfValue) 
     { 
      Type d1 = typeof(List<>); 

      Type[] typeArgs = { TypeOfValue }; 

      Type DynamicListType = d1.MakeGenericType(typeArgs); 


      object DynamicListObj = Activator.CreateInstance(DynamicListType); 


      DynamicList = Convert.ChangeType(DynamicListObj, DynamicListType); 


      foreach (object ValueElement in ValueRange) 
      { 
        dynamic el = Convert.ChangeType(ValueElement, TypeOfValue); 
        DynamicList.Add(el); 
      } 

     } 
     else //retrun empty List but with right type 
     { 
      Type d1 = typeof(List<>); 

      Type[] typeArgs = { CallingType }; 

      Type DynamicListType = d1.MakeGenericType(typeArgs); 

      object DynamicListObj = Activator.CreateInstance(DynamicListType); 

      DynamicList = Convert.ChangeType(DynamicListObj, DynamicListType); 
     } 

     return DynamicList; 
    } 

Ayrıca bir yere bir yakalama yakalayacağım.

nasıl test

   if (PropertyType == typeof(UInt32)) 
       { 
        List<UInt32> UInt32_test = NewProperty.ConvertList(PropertyType); 
       } 
       if (PropertyType == typeof(string)) 
       { 

        List<string> string_test = NewProperty.ConvertList(PropertyType); 
       } 
İlgili konular