Преобразовать список <T> в ObservableCollection <T> в WP7
Я не знаю, слишком ли поздно или что, но я не вижу, как это сделать...
То, что я ожидаю сделать, и что говорит браузер объектов, есть следующее:
var oc = new ObservableCollection<T>( new List<T>() );
Но ObservableCollection<T>
имеет единственный конструктор без параметров. В браузере объектов говорится, что есть 2 перегрузки, в которых должны быть переданы List и IEnuerable.
Что-то не так с моей настройкой? Являются ли конструкторы не в телефонной версии? (это было бы странно)
Если этого действительно не существует, каков стандартный способ сделать это с WP7 сейчас?
Ответы
Ответ 1
Судя по всему, ваш проект ориентирован на Windows Phone 7.0. К сожалению, конструкторы, которые принимают IEnumerable<T>
или List<T>
, недоступны в WP 7.0, только конструктор без параметров. Другие конструкторы доступны в Silverlight 4 и выше и WP 7.1 и выше, но не в WP 7.0.
Я полагаю, что ваш единственный вариант - взять ваш список и добавить элементы в новый экземпляр ObservableCollection
по отдельности, так как нет доступных готовых методов для их массового добавления. Хотя это не помешает вам самим применить это в расширении или статическом методе.
var list = new List<SomeType> { /* ... */ };
var oc = new ObservableCollection<SomeType>();
foreach (var item in list)
oc.Add(item);
Но не делайте этого, если вам это не нужно, если вы ориентируетесь на среду, которая обеспечивает перегрузки, а затем используйте их.
Ответ 2
ObservableCollection имеет несколько конструкторов, которые имеют входной параметр List <T> или IEnumerable <T> :
List<T> list = new List<T>();
ObservableCollection<T> collection = new ObservableCollection<T>(list);
Ответ 3
Чтобы преобразовать List<T> list
в наблюдаемую коллекцию, вы можете использовать следующий код:
var oc = new ObservableCollection<T>();
list.ForEach(x => oc.Add(x));
Ответ 4
Для этого вам нужно написать свой собственный метод расширения:
public static class CollectionEx
{
/// <summary>
/// Copies the contents of an IEnumerable list to an ObservableCollection
/// </summary>
/// <typeparam name="T">The type of objects in the source list</typeparam>
/// <param name="enumerableList">The source list to be converted</param>
/// <returns>An ObservableCollection containing the objects from the source list</returns>
public static ObservableCollection<T> ToObservableCollection<T>( this IEnumerable<T> enumerableList )
{
if( enumerableList != null ) {
// Create an emtpy observable collection object
var observableCollection = new ObservableCollection<T>();
// Loop through all the records and add to observable collection object
foreach( var item in enumerableList ) {
observableCollection.Add( item );
}
// Return the populated observable collection
return observableCollection;
}
return null;
}
}
Ответ 5
Метод расширения из этого ответа IList <T> к ObservableCollection <T> работает очень хорошо
public static ObservableCollection<T> ToObservableCollection<T>(this IEnumerable<T> enumerable) {
var col = new ObservableCollection<T>();
foreach ( var cur in enumerable ) {
col.Add(cur);
}
return col;
}
Ответ 6
ObservableCollection<FacebookUser_WallFeed> result = new ObservableCollection<FacebookUser_WallFeed>(FacebookHelper.facebookWallFeeds);
Ответ 7
Если вы собираетесь добавлять много элементов, подумайте о том, чтобы вывести свой собственный класс из ObservableCollection и добавить элементы к защищенному элементу Items - это не приведет к возникновению событий в наблюдателях. Когда вы закончите, вы можете поднять соответствующие события:
public class BulkUpdateObservableCollection<T> : ObservableCollection<T>
{
public void AddRange(IEnumerable<T> collection)
{
foreach (var i in collection) Items.Add(i);
OnCollectionChanged(new NotifyCollectionChangedEventArgs(NotifyCollectionChangedAction.Reset));
OnPropertyChanged(new PropertyChangedEventArgs("Count"));
}
}
При добавлении многих элементов в ObservableCollection, которые уже привязаны к элементу пользовательского интерфейса (например, LongListSelector), это может привести к большой разнице в производительности.
До добавления элементов вы также можете убедиться, что у вас достаточно места, чтобы список не расширялся, реализуя этот метод в классе BulkObservableCollection и вызывая его до вызова AddRange:
public void IncreaseCapacity(int increment)
{
var itemsList = (List<T>)Items;
var total = itemsList.Count + increment;
if (itemsList.Capacity < total)
{
itemsList.Capacity = total;
}
}
Ответ 8
Я сделал расширение, поэтому теперь я могу просто загрузить коллекцию с помощью списка:
MyObservableCollection.Load(MyList);
Расширение:
public static class ObservableCollectionExtension
{
public static ObservableCollection<T> Load<T>(this ObservableCollection<T> Collection, List<T> Source)
{
Collection.Clear();
Source.ForEach(x => Collection.Add(x));
return Collection;
}
}
Ответ 9
Использовать этот:
List<Class1> myList;
ObservableCollection<Class1> myOC = new ObservableCollection<Class1>(myList);
Ответ 10
Ответ, предоставленный Zin Min, решил мою проблему с помощью одной строки кода. Отлично!
У меня была такая же проблема с преобразованием общего списка в общий ObservableCollection, чтобы использовать значения из моего списка, чтобы заполнить ComboBox, который участвует в связывании через класс factory для окна WPF.
_expediteStatuses = new ObservableCollection <ExpediteStatus> (_ db.getExpediteStatuses());
Вот подпись для метода getExpediteStatuses:
public List <ExpediteStatus> getExpediteStatuses()