Aracılığıyla paylaş


Etkinlik Temsilcileri Kullanma

Etkinlik temsilcileri etkinlik yazarlarının, etkinlik kullanıcılarının etkinlik tabanlı işleyiciler sağlayabildiği belirli imzalarla geri çağırmaları kullanıma sunmasını sağlar. İki tür etkinlik temsilcisi kullanılabilir: ActivityAction<T> dönüş değeri olmayan etkinlik temsilcilerini tanımlamak için kullanılır ve ActivityFunc<TResult> dönüş değeri olan etkinlik temsilcilerini tanımlamak için kullanılır.

Etkinlik temsilcileri, bir alt etkinliğin belirli bir imzaya sahip olacak şekilde kısıtlanması gereken senaryolarda kullanışlıdır. Örneğin, bir While etkinlik kısıtlaması olmayan herhangi bir tür alt etkinlik içerebilir, ancak bir ForEach<T> etkinliğin gövdesi bir ActivityAction<T>'dir ve sonunda tarafından ForEach<T> yürütülen alt etkinlik, numaralandırdığı koleksiyonun InArgument<T> üyeleriyle aynı türde bir ForEach<T> alt etkinliğe sahip olmalıdır.

ActivityAction Kullanma

Çeşitli .NET Framework 4.6.1 etkinlikleri etkinlik ve etkinlik gibi Catch etkinlik eylemlerini ForEach<T> kullanır. Her durumda etkinlik eylemi, iş akışı yazarının bu etkinliklerden birini kullanarak bir iş akışı oluştururken istenen davranışı sağlamak için bir etkinlik belirttiği konumu temsil eder. Aşağıdaki örnekte, konsol penceresinde metin görüntülemek için bir ForEach<T> etkinlik kullanılır. gövdesiForEach<T>, dizesi olan türüyle ActivityAction<T> eşleşen bir ForEach<T> kullanılarak belirtilir. WriteLine içinde Handler belirtilen etkinliğin Text bağımsız değişkeni, etkinliğin yinelediği koleksiyondaki dize değerlerine ForEach<T> bağlıdır.

DelegateInArgument<string> actionArgument = new DelegateInArgument<string>();

Activity wf = new ForEach<string>
{
    Body = new ActivityAction<string>
    {
        Argument = actionArgument,
        Handler = new WriteLine
        {
            Text = new InArgument<string>(actionArgument)
        }
    }
};

List<string> items = new List<string>();
items.Add("Hello");
items.Add("World.");

Dictionary<string, object> inputs = new Dictionary<string, object>();
inputs.Add("Values", items);

WorkflowInvoker.Invoke(wf, inputs);

actionArgument, koleksiyondaki tek tek öğeleri WriteLine'a akıtmak için kullanılır. İş akışı çağrıldığında konsolda aşağıdaki çıkış görüntülenir.

HelloWorld.

Bu konudaki örneklerde nesne başlatma söz dizimi kullanılır. İş akışındaki etkinliklerin hiyerarşik bir görünümünü sağladığından ve etkinlikler arasındaki ilişkiyi gösterdiğinden, kodda iş akışı tanımları oluşturmak için nesne başlatma söz dizimi yararlı bir yol olabilir. Program aracılığıyla iş akışları oluştururken nesne başlatma söz dizimlerini kullanmanız gerekmez. Aşağıdaki örnek, işlevsel olarak önceki örne eşdeğerdir.

DelegateInArgument<string> actionArgument = new DelegateInArgument<string>();

WriteLine output = new WriteLine();
output.Text = new InArgument<string>(actionArgument);

ActivityAction<string> body = new ActivityAction<string>();
body.Argument = actionArgument;
body.Handler = output;

ForEach<string> wf = new ForEach<string>();
wf.Body = body;

List<string> items = new List<string>();
items.Add("Hello");
items.Add("World.");

Dictionary<string, object> inputs = new Dictionary<string, object>();
inputs.Add("Values", items);

WorkflowInvoker.Invoke(wf, inputs);

Nesne başlatıcıları hakkında daha fazla bilgi için bkz . Nasıl yapılır: Oluşturucu Çağırmadan Nesneleri Başlatma (C# Programlama Kılavuzu) ve Nasıl yapılır: Nesne Başlatıcısı Kullanarak Nesne Bildirme (Visual Basic).

Aşağıdaki örnekte, bir TryCatch iş akışında bir etkinlik kullanılır. bir ApplicationException iş akışı tarafından oluşturulur ve bir Catch<TException> etkinlik tarafından işlenir. Etkinliğin etkinlik eyleminin Catch<TException> işleyicisi bir WriteLine etkinliktir ve özel durum ayrıntıları kullanılarak exDelegateInArgument<T>bu eyleme akışı yapılır.

DelegateInArgument<ApplicationException> ex = new DelegateInArgument<ApplicationException>()
{
    Name = "ex"
};

Activity wf = new TryCatch
{
    Try = new Throw()
    {
        Exception = new InArgument<Exception>((env) => new ApplicationException("An ApplicationException was thrown."))
    },
    Catches =
    {
        new Catch<ApplicationException>
        {
            Action = new ActivityAction<ApplicationException>
            {
                Argument = ex,
                Handler = new WriteLine()
                {
                    Text = new InArgument<string>((env) => ex.Get(env).Message)
                }
            }
        }
    },
    Finally = new WriteLine()
    {
        Text = "Executing in Finally."
    }
};

bir tanımlayan ActivityAction<T>özel etkinlik oluştururken, bu InvokeAction<T>çağrıyı modellemek için bir ActivityAction<T> kullanın. Bu örnekte özel WriteLineWithNotification bir etkinlik tanımlanmıştır. Bu etkinlik, ardından bir Sequence dize bağımsız değişkeni alan bir WriteLine çağıran bir InvokeAction<T> etkinlik içeren bir ActivityAction<T> oluşur.

public class WriteLineWithNotification : Activity
{
    public InArgument<string> Text { get; set; }
    public ActivityAction<string> TextProcessedAction { get; set; }

    public WriteLineWithNotification()
    {
        this.Implementation = () => new Sequence
        {
            Activities =
            {
                new WriteLine
                {
                    Text = new InArgument<string>((env) => Text.Get(env))
                },
                new InvokeAction<string>
                {
                    Action = TextProcessedAction,
                    Argument = new InArgument<string>((env) => Text.Get(env))
                }
            }
        };
    }
}

Bir iş akışı etkinliği kullanılarak WriteLineWithNotification oluşturulduğunda, iş akışı yazarı etkinlik eyleminin Handleriçinde istenen özel mantığı belirtir. Bu örnekte, etkinliğini kullanan WriteLineWithNotification bir iş akışı oluşturulur ve WriteLine etkinliği olarak Handlerkullanılır.

// Create and invoke the workflow without specifying any activity action
// for TextProcessed.
Activity wf = new WriteLineWithNotification
{
    Text = "Hello World."
};

WorkflowInvoker.Invoke(wf);

// Output:
// Hello World.

// Create and Invoke the workflow with specifying an activity action
// for TextProcessed.
DelegateInArgument<string> msg = new DelegateInArgument<string>();
Activity wf2 = new WriteLineWithNotification
{
    Text = "Hello World with activity action.",
    TextProcessedAction = new ActivityAction<string>
    {
        Argument = msg,
        Handler = new WriteLine
        {
            Text = new InArgument<string>((env) => "Handler of: " + msg.Get(env))
        }
    }
};

// Invoke the workflow with an activity action specified
WorkflowInvoker.Invoke(wf2);

// Output:
// Hello World with activity action.
// Handler of: Hello World with activity action.

Bir veya daha fazla bağımsız değişkeni geçirmek için birden çok genel sürümü InvokeAction<T> vardır ve ActivityAction<T> sağlanır.

ActivityFunc kullanma

ActivityAction<T> , etkinlikten ActivityFunc<TResult> sonuç değeri olmadığında ve sonuç değeri döndürülürken kullanıldığında kullanışlıdır. bir tanımlayan ActivityFunc<TResult>özel etkinlik oluştururken, bu InvokeFunc<TResult>çağrıyı modellemek için bir ActivityFunc<TResult> kullanın. Aşağıdaki örnekte bir WriteFillerText etkinlik tanımlanmıştır. Dolgu metnini sağlamak için, InvokeFunc<TResult> tamsayı bağımsız değişkenini alan ve dize sonucuna sahip olan bir belirtilir. Dolgu metni alındıktan sonra konsolda bir WriteLine etkinlik kullanılarak görüntülenir.

public class WriteFillerText : Activity
{
    public ActivityFunc<int, string> GetText { get; set; }
    public InArgument<int> Quantity { get; set; }

    Variable<string> text = new Variable<string>
    {
        Name = "Text"
    };

    public WriteFillerText()
    {
        this.Implementation = () => new Sequence
        {
            Variables =
            {
                text
            },
            Activities =
            {
                new InvokeFunc<int, string>
                {
                    Func = GetText,
                    Argument = new InArgument<int>((env) => Quantity.Get(env)),
                    Result = new OutArgument<string>(text)
                },
                new WriteLine
                {
                    Text = new InArgument<string>(text)
                }
            }
        };
    }
}

Metni sağlamak için, bir int bağımsız değişken alan ve dize sonucu olan bir etkinlik kullanılmalıdır. Bu örnekte bu gereksinimleri karşılayan bir TextGenerator etkinlik gösterilmektedir.

public class TextGenerator : CodeActivity<string>
{
    public InArgument<int> Quantity { get; set; }
    public InArgument<string> Text { get; set; }

    protected override string Execute(CodeActivityContext context)
    {
        // Provide a quantity of Random Text
        int q = Quantity.Get(context);
        if (q < 1)
        {
            q = 1;
        }

        string text = Text.Get(context) + " ";
        StringBuilder sb = new StringBuilder(text.Length * q);
        for (int i = 0; i < q; i++)
        {
            sb.Append(text);
        }

        return sb.ToString();
    }
}

Etkinliği etkinlikle birlikte kullanmak TextGenerator için olarak belirtinWriteFillerText.Handler

DelegateInArgument<int> actionArgument = new DelegateInArgument<int>();

Activity wf = new WriteFillerText
{
    Quantity = 5,
    GetText = new ActivityFunc<int, string>
    {
        Argument = actionArgument,
        Handler = new TextGenerator
        {
            Quantity = new InArgument<int>(actionArgument),
            Text = "Hello World."
        }
    }
};

WorkflowInvoker.Invoke(wf);