Предположим, у меня есть два класса A
а также B
а также B
производный A
,
Класс А:
class A
{
public:
virtual const unsigned char* getArray()
{
return array;
}
protected:
unsigned char array[250];
};
Класс Б:
class B : public A
{
public:
virtual unsigned char* getArray()
{
return array;
}
};
Могу ли я создать класс C, который будет делать это?
class C
{
public:
const unsigned char* getArrayMiddle(A &a)
{
return (a.getArray() + 125);
}
unsigned char* getArrayMiddle(B &b)
{
return (b.getArray() + 125);
}
};
На этом простом примере я пытаюсь узнать, могу ли я создать два метода в классе C
один из них возвращает константный указатель, если этого требует тип получаемого объекта.
Будет ли компилятор автоматически вызывать правильный метод в C
в зависимости от типа параметра, даже если B
производный A
?
Чтобы уточнить, если у меня есть
A* obj = new B();
C c;
c.getArrayMiddle(*obj);
какая функция будет вызвана? Может ли это создать неожиданные ситуации?
Будет ли компилятор автоматически вызывать правильный метод в
C
в зависимости от типа параметра, даже еслиB
производныйA
?
Компилятор интерпретирует вызов метода как любой из двух методов в зависимости от статический (время компиляции) тип выражения аргумента. Считаете ли вы это право Полагаю, метод определяется тем, какой из них вы хотите вызвать.
Если статический тип аргумента B &
тогда второй вариант (возвращающий unsigned char *
) будет называться. Если это не B &
но это A &
тогда первый вариант (возвращение const unsigned char *
) будет называться.
Точные правила, определяющие, какой перегруженный метод вызывается, в каких обстоятельствах достаточно сложны, но в целом более конкретно подходящий кандидат обычно является предпочтительным. В этом случае B &
более конкретно, чем A &
, поэтому он будет вызываться, если аргумент действительно B &
хотя в этом случае он тривиально преобразуется в A &
из-за иерархии наследования.
тем не мение, Стоит отметить, что (согласно комментарию cpplearner) ваш код, как опубликовано, не должен компилироваться. B
не должно быть в состоянии переопределить getArray
с версией, которая опускает const
Классификатор. G ++ 5.4 диагностирует это как ошибку. Вместо этого вы можете не иметь один метод, переопределяющий другой: отбросьте virtual
спецификатор, или дать им другое имя, или пометить метод в A
как const
метод.
Других решений пока нет …