Форум программистов
 

Восстановите пароль или Зарегистрируйтесь на форуме, о проблемах и с заказом рекламы пишите сюда - alarforum@yandex.ru, проверяйте папку спам!

Вернуться   Форум программистов > IT форум > Помощь студентам
Регистрация

Восстановить пароль
Повторная активизация e-mail

Купить рекламу на форуме - 42 тыс руб за месяц

Ответ
 
Опции темы Поиск в этой теме
Старый 16.03.2016, 16:57   #1
max_prorok
Форумчанин
 
Регистрация: 06.10.2011
Сообщений: 181
По умолчанию C# События. "Короткая" и "длинная" записи.

Уважаемые форумчане. Пытаюсь разобраться в событиях. Возник следующий вопрос.

Как я понял есть короткая (сокращенная) запись определения события. Выглядит она вот так:
Код:
public event EventHandler<CarInfoEventArgs> NewCarInfo;
В приведенном выше строчке класс CarInfoEventArgs наследуется от EventArgs. Это пример из книги.
В ней же пишется, что длинная форма сокращенной нотации выглядит следующим образом:
Код:
private delegate EventHandler<CarInfoEventArgs> newCarInfo;
public event EventHandler<CarInfoEventArgs> NewCarInfo
{
	add
	{
		newCarInfo+=value;
	}
	remove
	{
		newCarInfo-=value;
	}
}
Ну коль учебник утверждает, что это эквивалентная запись, то думаю заменю сокращенную нотацию на полную, за одно добавлю вывод на консоль сообщения о том, что добавился новый подписчик. Но не тут-то было. Приведу полный листинг рабочего кода.
Код:
using System;

public class Test
{
	public static void Main()
	{
		var oleg = new CarDealer("Oleg");
		var vasya = new CarDealer("Vasya");
		var misha = new Consumer("Misha");
		oleg.NewCarInfo+=misha.NewCarIsHere;
		oleg.NewCar("Ferrari");
		vasya.NewCar("ZAZ");
		vasya.NewCarInfo+=misha.NewCarIsHere;
		var maks = new Consumer("Max");
		vasya.NewCarInfo+=maks.NewCarIsHere;
		oleg.NewCar("Opel");
		vasya.NewCar("VAZ");
		vasya.NewCar("UAZ");
		oleg.NewCar("Renault");
		oleg.NewCarInfo+=maks.NewCarIsHere;
		oleg.NewCar("Peugeot");
		vasya.NewCarInfo-=maks.NewCarIsHere;
		oleg.NewCar("Mazda");
		oleg.NewCarInfo-=misha.NewCarIsHere;
		vasya.NewCar("GAZ");
	}
}

public class CarInfoEventArgs: EventArgs
{
	public CarInfoEventArgs(string car)
	{
		this.Car=car;
	}
	public string Car {get; private set;}
}

public class CarDealer
{
	public event EventHandler<CarInfoEventArgs> NewCarInfo;
	public string dealer {get; private set;}
	public CarDealer (string dealer)
	{
		this.dealer=dealer;
		Console.WriteLine("New car dealer - {0}", dealer);
	}
	public void NewCar(string car)
	{
		Console.WriteLine("{0}, new car {1}", dealer, car);
		RaiseNewCarInfo(car);
	}
	protected virtual void RaiseNewCarInfo(string car)
	{
		EventHandler<CarInfoEventArgs> newCarInfo = NewCarInfo;
		if (newCarInfo !=null)
		{
			newCarInfo(this, new CarInfoEventArgs(car));
		}
	}
}

public class Consumer
{
	private string name;
	public Consumer(string name)
	{
		this.name=name;
		Console.WriteLine("New car consumer - {0}", name);
	}
	
	public void NewCarIsHere(object sender, CarInfoEventArgs e)
	{
		Console.WriteLine("{0}: car {1} is new", name, e.Car);
	}
}
Такой код выполняется. Но если я заменю строку
Код:
public event EventHandler<CarInfoEventArgs> NewCarInfo;
на
Код:
private delegate EventHandler<CarInfoEventArgs> newCarInfo;
public event EventHandler<CarInfoEventArgs> NewCarInfo
{
	add
	{
		newCarInfo+=value;
	}
	remove
	{
		newCarInfo-=value;
	}
}
Компилятор выдает ошибку, что не хватает открывающейся круглой скобки в строке с объявлением приватного делегата. Ну думаю, не хватает в объявлении делегата параметров, дай допишу. Привел строку эту к такому виду:
Код:
private delegate EventHandler<CarInfoEventArgs> newCarInfo (object sender, CarInfoEventArgs e);
После этого он стал выдавать ошибку, что внутри блоков add и remove переменная CarDealer.newCarInfo является "тип", который недопустим в данном контексте.
Думаю, ладно. Пойду по пути наименьшего сопротивления. Просто удалю эту строчку, авось компилятор сам за меня создаст этот делегат, тем более на хабре нашел какую-то статью, в которой длинная запись события используется именно без объявления приватного делегата. Значит меняю код события на следующий:
Код:
public event EventHandler<CarInfoEventArgs> NewCarInfo
{
	add
	{
		NewCarInfo+=value;
	}
	remove
	{
		NewCarInfo-=value;
	}
}
Опять ошибка, но на этот раз уже компилятор ссылается на строчку в методе RaiseNewCarInfo(), а именно на эту:
Код:
EventHandler<CarInfoEventArgs> newCarInfo = NewCarInfo;
И говорит, что, мол, событие CarDealer.NewCarInfo может находиться только в левой части операции += или -=.

Люди добрые, помогите разобраться, как в данном случае использовать полную запись события?
max_prorok вне форума Ответить с цитированием
Ответ


Купить рекламу на форуме - 42 тыс руб за месяц



Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
Для заданной строки определить все входящие в неё символ. Например: строка "abccbbabbac" состоит из символов "a", "b" и "c" Sandakan01 Помощь студентам 1 24.02.2016 03:20