Задать вопрос
Dyikot
@Dyikot

Почему выдает ошибку при наследовании?

Если пропишу все наследуемые переменные в наследуемом классе через this, то ошибка уходит.Почему так?
template <typename T>
class Array
{
protected:
	T* _data;
	unsigned int _size, _capasity;
	const int _defaultCapasity = 4;

	virtual void PushWithResize(const T& item) = 0;
public:
	Array()
	{
		_size = 0;
		_capasity = _defaultCapasity;
		_data = new T[_defaultCapasity];
	}

	Array(int size)
	{
		_size = size;
		_capasity = size > _defaultCapasity ? size : _defaultCapasity;
		_data = new T[_capasity];
	}

	~Array()
	{
		delete[]  _data;
	}
	int Size()
	{
		return _size;
	}
	bool IsEmpty()
	{
		return _size == 0;
	}
	virtual void Pop() = 0;

};

Производный класс:
template <typename T>
class Queue : public Array<T>
{
private:
	int _firstItemShift = 0;

	void PushWithResize(const T& item) override
	{
		_capasity *= 1.5;
		T* data = new T[_capasity];

		for (int index = 0; index < _size; index++)
		{
			data[index] = _data[index + _firstItemShift];
		}
		data[_size] = item;
		delete[] _data;
		_data = data;
	}
public:
	Queue() : Array<T>()
	{
		_firstItemShift = 0;
	}

	Queue(int size) :Array<T>(size)
	{
		_firstItemShift = 0;
	}

	void Push(const T& item)
	{
		int size = _size + 1;

		if (size > _capasity)
		{
			PushWithResize(item);
		}
		else
		{
			_data[_size] = item;
		}
		_size = size;
	}

	void Pop() override
	{
		if (_size - 1 >= 0)
		{
			_size--;
		}
		else
		{
			return;
		}
		_firstItemShift++;
	}

	T& Front()
	{
		return _data[_firstItemShift];
	}

	T& Back()
	{
		return _data[_size - 1];
	}
};

Ошибки: Compiler Error C3861,Compiler Error C2065.
  • Вопрос задан
  • 77 просмотров
Подписаться 1 Простой Комментировать
Решения вопроса 1
wataru
@wataru Куратор тега C++
Разработчик на С++, экс-олимпиадник.
Для решения этой проблемы по уму надо написать вот это в определении производного класса:
using Array<T>::_size;
using Array<T>::_capasity;
using Array<T>::_data;


Ответ на вопрос "почему" в С++ всегда один: "потому что стандарт":
Non-dependent names are looked up and bound at the point of template definition. This binding holds even if at the point of template instantiation there is a better match:


Проблема в том, что Array зависит от T, а вот его член _size от T не зависит. Ну вот не ищет компилятор независимые имена в зависимых местах. Независимые имена разрешаются в месте определения шаблона, когда еще неясно даже, с каким оно типом будет работать-то. Поэтому он никак до Array достучатся не может, ведь никакого T конкретного у него еще нет.

Надо как-то компилятору указать, где искать вот эти ваши _size и т.д.
Например, через this-> или через using или через Array<T>::.

Вообще от этих правил lookup-а в C++ волосы дыбом встают и куча приколов вылезает. Их надо только запомнить. Оно неинтуитивно, но таково оно есть.
Ответ написан
Комментировать
Пригласить эксперта
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Похожие вопросы