Рекомендован ли мой подход к присвоению значений экземпляру пользовательских EventArgs? - PullRequest
0 голосов
/ 03 октября 2010

В моей текущей ситуации у меня есть класс, который выполняет операцию синхронно.Во время этой операции определенное событие будет выдано несколько раз, в зависимости от того, как часто возникает ситуация, когда возникает событие.
Я знаю, как работает механизм событий и каковы рекомендуемые способы использования.Работает хорошо. (Примечание: мое приложение однопоточное)

Я хочу установить значение для свойства в моих EventArgs.У меня никогда не было необходимости устанавливать свойства там.

Это упрощенная ситуация моей текущей ситуации: (Обратите внимание, мне не нужны ответы, говорящие мне, чтобы использовать регулярное выражение или stringreplace, потому что это выиграло 'в этой ситуации не работает)

У меня есть EventArgs:

public class TestEventArgs : EventArgs
{

    public String OldString { get; private set; }
    public String NewString { get; set; }

    public TestEventArgs(String oldString)
    {
        this.OldString = oldString;
    }
}

Обычно я вызываю события следующим образом:

public event EventHandler<TestEventArgs> ChangeString;

protected virtual void OnChangeString(String oldString)
{
    EventHandler<TestEventArgs> handler = this.ChangeString;
    if (handler != null)
    {
        handler(this, new TestEventArgs(oldString));
    }
}

и вызывая метод OnChangeString,потому что я прочитал это таким образом, чтобы вызывать события давным-давно.

Модифицированный код, в котором мне нужно значение EventArgs после его поднятия:

public event EventHandler<TestEventArgs> ChangeString;

protected virtual void OnChangeString(TestEventArgs args)
{
    EventHandler<TestEventArgs> handler = this.ChangeString;
    if (handler != null)
    {
        handler(this, args);
    }
}
    public void Foo()
    {
        String oldString = "this is the old string";
        // this.OnChangeString(oldString) // this is the way I called before
        // now I need to keep a reference to the EventArgs
        TestEventArgs args = new TestEventArgs(oldString);
        this.OnChangeString(args);
        // here I do have full access to args.NewString
    }

Итак, действительно ли этохорошо, чтобы сохранить ссылку на EventArgs и вызвать событие с помощью метода, который принимает мои EventArgs в качестве параметра?

Ответы [ 3 ]

1 голос
/ 03 октября 2010

Если я правильно понял ваш вопрос, вы, как правило, не хотите хранить ссылку на ваш TestEventArg и повторно использовать этот объект для другого события.

В вашем случае ваш TestEventArg имеет публичный вызов свойств NewString. Если какой-либо обработчик событий обновляет это свойство, в то время как оно является ссылкой начала для нескольких частей вашей программы, вы можете случайно столкнуться с проблемой, когда свойство NewString продолжало изменяться по сравнению с другой частью вашей проблемы.

Однако, если ваш TestEventArg имеет только читаемое свойство, я не вижу проблем с сохранением ссылки и ее повторным использованием.

public class TestEventArgs : EventArgs
{    
    public String OldString { get; private set; }
    public String NewString { get; private set; }

    public TestEventArgs(String oldString, String newString)
    {
        this.OldString = oldString;
        this.NewString - newString
    }
}

Как правило, вы хотите, чтобы ваше событие arg оставалось неизменным , что облегчит понимание и отладку вашей программы.

1 голос
/ 03 октября 2010

Аргумент TestEventArg сохраняется только в том случае, если вам нужен доступ к переменной после вызова метода.Примером этого является OnClosing событие для формы.У него есть переменная, которую вы можете установить, чтобы сказать ей отменить закрытие.В этом случае, если клиент регистрирует обратный вызов и может установить свойство для класса TestEventArg, тогда вы захотите, чтобы переменная указывала на него.Если все, что вы хотите сделать, это передать информацию в обратный вызов и ничего не нужно возвращать, тогда я использую первый метод.

Одно предостережение для меня заключается в том, что если я использую метод OnChangeString,Я пишу это так, чтобы он инкапсулировал детали аргументов события.

protected virtual void OnChangeString(string oldString)
{
    EventHandler<TestEventArgs> handler = this.ChangeString;
    if (handler != null)
    {
        var args = new TestEventArgs(oldString);
        handler(this, args);

        // Do something with args
    }
}
1 голос
/ 03 октября 2010

Я думаю, что ваш вопрос сводится к:

Можно ли использовать аргументы события для передачи данных обратно источнику события?

Прежде всего: на низком уровне это будет работать. Вы можете изменить объект события, и вы можете увидеть эти изменения в коде, который вызывает событие.

Но что, если есть несколько слушателей событий? Кто может установить NewString?

Если вы ожидаете только одного, более ясно передать делегат (типа Func<String, String>) классу, который теперь вызывает событие.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...