سؤال

عندما Expression<T> جمعت هو الناتجة رمز ضمنا مؤقتا من قبل الإطار ؟ أنا أفكر على طول خطوط ثابتة Regex أساليب أين إطار ضمنا يجمع ومخابئ القليلة الماضية regexes.

إذا جمعت Expression<T> الكائنات لا مؤقتا ، يمكن أن يوصي بعض أفضل الممارسات من أجل الحفاظ على وقت التحويل البرمجي أسفل أو أي gotchas التي يمكن أن يسبب مشاكل إذا كنت ذاكرة التخزين المؤقت يدويا وهو التعبير ؟

public MyResultType DoSomething(int arg1, int arg2)
{
    var result = invokeHandler(
        (IDoSomethingHandler h) => h.DoSomething(arg1, arg2)
    );
    return result;
}

private TResult invokeHandler<T, TResult>(Expression<Func<T, TResult>> action)
    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);

    return result;
}

في هذا المثال, أنا قلقة بعض الشيء من أنه إذا لم ذاكرة التخزين المؤقت جمعت التعبير ، أنه سيتم استخدام القيم arg1 و arg2 كما كانت في ذلك الوقت التعبير جمعت بدلا من استرجاع تلك القيم من المكان المناسب في المكدس (أيبدلا من الحصول على القيم الحالية).

هل كانت مفيدة؟

المحلول

لا ؛ أنا لا أعتقد أنه هو ؛ إذا كنت تريد ذلك مؤقتا ، يجب أن تضغط على Delegate إشارة (عادة Func<...> أو Action<...>).وبالمثل ، إذا كنت ترغب في الحصول على أفضل أداء ، تجمع على أنها parameterised التعبير ، حتى تتمكن من ارسال قيم مختلفة عند الاحتجاج بها.

في هذه الحالة إعادة صياغة شأنها أن تساعد:

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;
}

أيجعل أعداد المعلمات من التعبير ، وتمرير الفعلية منها أنه في وقت التشغيل (بدلا من الثوابت في التعبير).

نصائح أخرى

امدا experssions لم يتم التخزين المؤقت تلقائيا.سوف تحتاج إلى تنفيذ كنت تملك التخزين المؤقت/التحفيظ خوارزميات ذلك.تحقق ذات الصلة ستاكوفيرفلوو السؤال:

هل من الممكن أن ذاكرة التخزين المؤقت قيمة تقييمها في امدا التعبير ؟

من المهم أن نلاحظ أن تعبيرات لامدا كسالى تقييمها في C#.

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top