Кажется, я решил проблему. Я переработал оставшуюся часть проекта, то есть реализацию IClassFactory, а также реализацию интерфейса IUnknown класса shellextension с целью понять, для чего эти «вещи» используются в этом проекте.
При этом я обнаружил некоторые ошибки, неинициализированные переменные, приведение к неправильным типам и т. Д. Я также изменил некоторые счетчики с UINT на LONG, чтобы я мог использовать InterlockedIncrement вместо ++. И после этого проблема, похоже, исчезла. Я не могу точно сказать, какая ошибка вызвала AccessViolationException, но в конце ее не было в методе QueryContextMenu, как я думал ...
Нет; я не полагаю, что это; если Вы хотите кэшируемый, необходимо держать на Delegate
ссылка (обычно Func<...>
или Action<...>
). Аналогично, если бы Вы хотите получить лучшую производительность, Вы скомпилировали бы ее как параметризованное выражение, таким образом, можно отправить в различных значениях при вызове ее.
В этом случае, перефразирование помогло бы:
public MyResultType DoSomething(int arg1, int arg2)
{
var result = invokeHandler(
(IDoSomethingHandler h, int a1, int a2) => h.DoSomething(a1, a2),
arg1, arg2);
return result;
}
private TResult invokeHandler<T, TResult>(Expression<Func<T,int,int,TResult>> action,
int arg1, int arg2)
where T : class
{
// Here, I might want to check to see if action is already cached.
var compiledAction = action.Compile();
var methodCallExpr = action as MethodCallExpression;
// Here, I might want to store methodCallExpr in a cache somewhere.
var handler = ServiceLocator.Current.GetInstance<T>();
var result = compiledAction(handler, arg1, arg2);
return result;
}
т.е. делают параметры чисел выражения и передают фактический это во времени выполнения (вместо того, чтобы быть константами в выражении).
Выражения лямбды не кэшируются автоматически. Необходимо будет реализовать Вас, владеют caching/memoization алгоритмами для этого. Проверьте связанный вопрос о Stackoverflow:
это возможный кэшировать значение, оцененное в лямбда-выражении?
важно отметить, что лямбда-выражения ленивы оцененный в C#.