Поскольку ваш метод accept()
на самом деле не вызывает ни один из методов visit()
, ни один.:)
Однако, если вы вызвали его как:
void accept(Interface_Test_Visitor v)
{
Console.WriteLine("Accepting visitor.");
v.Visit(this); // lets invoke it this time
}
, компилятор увидит, что this
сначала как экземпляр USB_Read_Test
, затем Interface_Read_Test_Case
, затем Interface_Test_Case
.Сначала он выберет наиболее прямую перегрузку (или ту, в которой могут использоваться неявные преобразования), затем пойдет по цепочке наследования, пока не найдет подходящий тип, подходящий для перегрузки.Так что в этом случае он будет вызывать visit(USB_Read_Test)
.Вы можете переопределить это поведение, приведя:
v.Visit((Interface_Read_Test_Case)this); // argument is an instance of Interface_Read_Test_Case
v.Visit((Interface_Test_Case)this); // argument is an instance of Interface_Test_Case
Если, однако, ваш класс реализует несколько интерфейсов, где у каждого интерфейса есть перегрузка, но нет ни одного для класса, вы получите ошибки неоднозначности, которые вам придется устранить.
например,
interface IX { }
interface IY { }
class Class : IX, IY { }
void Call(IX _) { }
void Call(IY _) { }
// no Call(Class _) method
var c = new Class();
Call(c); // error: ambiguous call
Call((IX)c); // not ambiguous
Для получения дополнительной информации см. Порядок разрешения методов и слегка связанные C #: передача нулевого значения перегруженному методу - какой метод вызывается.