Мне нужно, чтобы некоторая информация передавалась в виде лямбда-выражения некоторым методам. По сути, это способ добавить информацию в запрос к базе данных. Простой пример будет:
companyData.GetAll(
where => "SomeField = @SOMEFIELD",
order => "Id",
SOMEFIELD => new Parameter {DbType = DbType.String, Value = "some value"}
)
Работает довольно хорошо, за исключением того, что мне нужно вызвать LambdaExpression.Compile , чтобы получить объект параметра, который оказывает большое влияние на производительность.
Чтобы получить более быстрые результаты, я пришел с этим наивным тестом кэширования:
class ExpressionCache<T,U>
{
private static ExpressionCache<T, U> instance;
public static ExpressionCache<T, U> Instance
{
get
{
if (instance == null) {
instance = new ExpressionCache<T, U>();
}
return instance;
}
}
private ExpressionCache() { }
private Dictionary<string, Func<T, U>> cache = new Dictionary<string, Func<T, U>>();
public Func<T, U> Get(Expression<Func<T, U>> expression)
{
string key = expression.Body.ToString();
Func<T,U> func;
if (cache.TryGetValue(key, out func)) {
return func;
}
func = expression.Compile();
cache.Add(key, func);
return func;
}
}
Этот класс имел огромное значение: от 35000 миллисекунд на 10000 итераций до 700.
Теперь возникает вопрос: с какой проблемой я столкнусь, используя тело выражения в качестве ключа для словаря?