У меня есть класс, реализующий интерфейс, который имеет конструктор с несколькими параметрами и статическую отсортированную коллекцию. Этот класс является базовым классом, который имеет множество унаследованных классов.
internal class SCO : IVotable
{
public SCO(SPListItem item, List<Vote> votes)
{
//Initialize Object
}
public static List<T> SortedCollection<T>(SPListItemCollection items, ListSortType sortType, List<Vote> votes) where T : IVotable
{
var returnlist = new List<T>();
Type genericType = typeof(T);
for (int i = 0; i < items.Count; i++) { returnlist.Add((T)Activator.CreateInstance(genericType, new object[] { items[i], votes })); }
switch (sortType)
{
case ListSortType.Hot:
returnlist.Sort((p1, p2) => p2.HotScore.CompareTo(p1.HotScore));
break;
case ListSortType.Top:
returnlist.Sort((p1, p2) => p2.VoteTotal.CompareTo(p1.VoteTotal));
break;
case ListSortType.Recent:
returnlist.Sort((p1, p2) => p2.CreatedDate.CompareTo(p1.CreatedDate));
break;
}
return returnlist;
}
}
Это позволяет мне делать следующее с любым дочерним классом:
List<ChildClass> sortedClassList = ChildClass.SortedCollection<ChildClass>(listItems, sortType, votes);
Моя текущая зависимость от Activator.CreateInstance меня беспокоит, так как это примерно в 100 раз медленнее, чем непосредственное использование Emit IL. Я читал несколько статей об Emit IL, и это решение кажется фантастическим.
Однако я не могу заставить его работать. Когда я пытаюсь создать экземпляр ILGenerator gen =
, он говорит мне: «Не удается получить доступ к методу нестатического поля в статическом контексте».
Мой класс не является статическим, как и мои конструкторы, а статический список, показанный ниже, еще не взаимодействует с Emit. Как мне заставить это работать?
Код до сих пор:
internal class SCO : IVotable
{
//Properties emittied
static ConstructorInfo ctor = typeof(SCO).GetConstructors()[1];
delegate SCO SCOCtor(SPListItem item, List<Vote> votes);
static SCOCtor SCOCtorDelegate;
DynamicMethod method = new DynamicMethod("CreateInstance", typeof (SCO),
new Type[] {typeof (SPListItem), typeof (List<Vote>)});
ILGenerator gen = method.GetILGenerator(); //Error here
//"Cannot access non-static field 'method' in static context"
private static SCO CreateInstance(SPListItem item, List<Vote> votes)
{
return SCOCtorDelegate(item, votes);
}
}
Блог для справки: http://ayende.com/blog/3167/creating-objects-perf-implications
Post : SCO
, который можно вызвать с помощью:List<Post> sortedPosts = Post.SortedCollection<Post>(listItems, sortType, votes);
- person Wesley   schedule 27.08.2012