سؤال

لقد كنت أبحث في التفكير.تنبعث منها مؤخرا.كتبت برنامج بسيط يولد DynamicMethod التي المكالمات بسيطة طريقة أخرى مع نفس المعلمات

class Program
{
    static void Main(string[] args)
    {
        Program p = new Program();
        p.Test();
    }

    public delegate void TestHandler(int a, int b, int c, int d, int e, int f);

    public void Test()
    {
        DynamicMethod method = new DynamicMethod(string.Empty, typeof(void), new[] { typeof(Int32), typeof(Int32), typeof(Int32), typeof(Int32), typeof(Int32), typeof(Int32) }, typeof(Program));


        MethodInfo method1 = typeof(Program).GetMethod("Question",BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic,null,new Type[]{typeof(Int32),typeof(Int32),typeof(Int32),typeof(Int32),typeof(Int32),typeof(Int32)},null);
        MethodInfo method2 = typeof(MethodBase).GetMethod("GetCurrentMethod", BindingFlags.Static | BindingFlags.Public | BindingFlags.NonPublic, null, new Type[] { }, null);
        MethodInfo method3 = typeof(Console).GetMethod("WriteLine", BindingFlags.Static | BindingFlags.Public | BindingFlags.NonPublic, null, new Type[] { typeof(Object) }, null);

        ILGenerator gen = method.GetILGenerator();

        gen.Emit(OpCodes.Nop);
        gen.Emit(OpCodes.Ldarg_S, 0);
        gen.Emit(OpCodes.Ldarg_S, 1);
        gen.Emit(OpCodes.Ldarg_S, 2);
        gen.Emit(OpCodes.Ldarg_S, 3);
        gen.Emit(OpCodes.Ldarg_S, 4);
        gen.Emit(OpCodes.Ldarg_S, 5);
        gen.Emit(OpCodes.Ldarg_S, 6);
        gen.Emit(OpCodes.Call, method1);
        gen.Emit(OpCodes.Nop);
        gen.Emit(OpCodes.Call, method2);
        gen.Emit(OpCodes.Call, method3);
        gen.Emit(OpCodes.Nop);
        gen.Emit(OpCodes.Ret);

        TestHandler handler = method.CreateDelegate(typeof(TestHandler)) as TestHandler;
        handler(1, 2, 3, 4, 5, 6);
    }

    public void Question(int a, int b, int c, int d, int e, int f)
    {
        Console.WriteLine("{0},{1},{2},{3},{4},{5}", a, b, c, d, e, f);
    }
}

عند تشغيل هذا المثال أنه وأتوقع أن الناتج 1,2,3,4,5,6 ومع ذلك ، فإنه إخراج 2,3,4,5,6,1

أنا لست متأكدا لماذا...إذا يا رفاق أعرف من أي موارد جيدة باستخدام التفكير.تنبعث منها يمكن أن تشير في هذا الاتجاه.لقد تم استخدام عاكس مع تنبعث من الدين.

هتافات

روهان

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

المحلول

والمشكلة التي تواجهها هي أنك الاحتجاج طريقة ديناميكية وليست ثابتة. لايوجد طريقة ولدت لديك إشارة إلى مثيل الطبقة البرنامج.

لاحظ أيضا كنت تدفع 7 المعلمات إلى المكدس لطريقة 6 المعلمة. يجب أن تكون المعلمة الأولى إشارة إلى الكائن الذي استدعاء الأسلوب جرا.

وسلوك غريب كنت ترى قد يكون بسبب عدم وجود معلمة مؤشر 6، والتفاف حول العودة إلى بداية صفيف معلمة.

وانظر. "كيفية: تحديد وتنفيذ طرق الحيوي" في مساعدة VS

ويمكنك الحصول على عمل من خلال قبول معلمة الكائن على في استدعاء الأسلوب الخاص بك، أو جعلها ثابتة:

ومندوب العام الفراغ TestHandler (يعترض سبيل المثال، كثافة العمليات لذلك، الباحث ب، ج الباحث، الباحث د، ه الباحث، الباحث و)؛

public void Test()
{
    DynamicMethod method = new DynamicMethod(string.Empty, typeof(void), new[] { typeof(object), typeof(Int32), typeof(Int32), typeof(Int32), typeof(Int32), typeof(Int32), typeof(Int32) }, typeof(Program));


    MethodInfo method1 = typeof(Program).GetMethod("Question", BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic, null, new Type[] { typeof(Int32), typeof(Int32), typeof(Int32), typeof(Int32), typeof(Int32), typeof(Int32) }, null);
    MethodInfo method2 = typeof(MethodBase).GetMethod("GetCurrentMethod", BindingFlags.Static | BindingFlags.Public | BindingFlags.NonPublic, null, new Type[] { }, null);
    MethodInfo method3 = typeof(Console).GetMethod("WriteLine", BindingFlags.Static | BindingFlags.Public | BindingFlags.NonPublic, null, new Type[] { typeof(Object) }, null);

    ILGenerator gen = method.GetILGenerator();

    gen.Emit(OpCodes.Nop);
    gen.Emit(OpCodes.Ldarg_S, 0);
    gen.Emit(OpCodes.Ldarg_S, 1);
    gen.Emit(OpCodes.Ldarg_S, 2);
    gen.Emit(OpCodes.Ldarg_S, 3);
    gen.Emit(OpCodes.Ldarg_S, 4);
    gen.Emit(OpCodes.Ldarg_S, 5);
    gen.Emit(OpCodes.Ldarg_S, 6);
    gen.Emit(OpCodes.Call, method1);
    gen.Emit(OpCodes.Nop);
    gen.Emit(OpCodes.Call, method2);
    gen.Emit(OpCodes.Call, method3);
    gen.Emit(OpCodes.Nop);
    gen.Emit(OpCodes.Ret);

    TestHandler handler = method.CreateDelegate(typeof(TestHandler)) as TestHandler;
    handler(this, 1, 2, 3, 4, 5, 6);
}

public void Question(int a, int b, int c, int d, int e, int f)
{
    Console.WriteLine("{0},{1},{2},{3},{4},{5}", a, b, c, d, e, f);
}

نصائح أخرى

أن تجعل من العمل يجب أن

  1. جعل Question a static طريقة
  2. التعليق gen.Emit(OpCodes.Ldarg_S,6);
  3. تعديل MethodInfo method1 = ... وفقا لذلك

واحد "رائحة" هو الذي وقف في التصحيح على Question طريقة لا يمكنك تقييم this المرجعية.وهذا لا ينبغي أن يكون أسلوب مثيل...;-)

تحرير:مكتب خدمات المشاريع.لقد رأيت للتو الجواب من روبرت واغنر الذي هو أفضل بكثير أوضح من الألغام.على استعداد لإلغاء منصبي إذا لزم الأمر...:-)

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