Если у вас есть MyCallback<Event>
, вы говорите, что у вас есть метод, который может принимать любой тип события. Он может принимать EventOne
, или EventTwo
, или SomeOtherEvent
.
Скажем, я называю RegisterCallback
и передать в делегат, указывая на способ с этой подписью:
public static void Foo(SomeOtherEvent arg)
Если ваш код будет работать, и я мог бы назначить, что к MyCallback<Event>
, то я мог бы пройти в EventOne
экземпляр этого метода при его вызове. Это, очевидно, проблема.
Для этого существует термин; вы ожидаете, что MyCallback
будет covariant относительно его общего аргумента. Фактически, это contravariant. Если у меня есть метод, который может принять любой случай, я могу четко передать в SomeEvent
или SomeOtherEvent
, то есть я мог бы назначить MyCallback<Event>
MyCallback<SomeOtherEvent>
, а не наоборот.
Если вы хотите сообщить компилятору, что: «Я знаю, что этот метод не может быть вызван с любым типом события, но я хочу, чтобы вы разрешили эту проверку и только не выполнялись во время выполнения, если данный аргумент не относится к надлежащего типа ". то вы можете сделать это, предполагая, что вы действительно имеете способ обеспечить, чтобы вы вызывали каждый обратный вызов с соответствующими аргументами. Вы не можете просто сделать бросок; вам необходимо обернуть метод новым методом, который выполняет литье:
eventTable.Add("test", e => callback((T)e));
Почему вы вообще используете дженерики? Должен работать с простым полиморфизмом при использовании .NET 3.5 или выше. –
Главным образом для обеспечения правильной регистрации типов и обеспечения более конкретной обработки делегатов. Я хочу, чтобы programmitcally ограничивал, что вызывающий объект RegisterCallback ожидает объект типа T в своем конечном делете. Это позволит мне сделать что-то вроде RegisterCallback (MyFunction), где MyFunction (ThisOddType objectIKnowAbout) –
user3130210
@ user3130210 Как вы планируете гарантировать, что вызовы вызываются с соответствующими аргументами? – Servy