Иллюстрированный самоучитель по Visual Studio .NET

Конструкторы и операции

Важными моментами в жизни объектов являются те, когда они копируются или создаются на основе уже существующих. Реализация конструктора копирования объектов просто обязательна, если вы пользуетесь контейнером объектов. В случае отсутствия или некорректного тела конструктора контейнеры откажутся работать с объектами класса. Обычным приемом при этом является реализация в классе операции присвоения operator= () и последующее ее воспроизведение в конструкторе копирования. Обратите внимание на тип возвращаемого значения операции присвоения. Это ссылка (CPolygon&) на активный или стоящий в левой части операции присвоения – *this, объект класса:

CPolygoni CPolygon:: operator=(const CPolygonS poly){
//====== Копируем все данные
m_pDoc = poly.m_pDoc;
m_nPenWidth = poly.m_nPenWidth;
m_PenColor = poly.m_PenColor;
m_BrushColor = poly.m_BrushColor;
m_ptLT = poly.m_ptLT;
m_ptRB = poly.m_ptRB;
//===== Освобождаем контейнер точек
if (!m_Points.empty()) m_Points.clear();
//====== Копируем все точки. Возможно решение с помощью assign.
for (OINT i=0; i<poly.m_Points.size();
m_Points.push_back(poly.m_Points[i])
//====== Возвращаем собственный объект
return *this;
//====== Конструктор копирования пользуется уже
//====== существующей реализацией операции присвоения
CPolygon::CPolygon(const CPolygoni poly)
{
*this = poly;
}

Довольно часто во вновь создаваемых классах переопределяют операцию выбора с помощью угловых скобок ([ ]). Смысл этой операции задает программист. Он часто бывает очевидным для классов объектов, содержащих внутри себя контейнеры, как в нашем случае. Так, если к полигону poly применить операцию выбора, например:

CDPoint pt = poly[i];

То он возвратит свою i-ю точку, что, безусловно, имеет смысл. Если же операция [ ] возвращает ссылку на i-ю точку, то становится возможным использовать ее и в левой части операции = (присвоения). Например:

poly[i] = CDPoint (2.5, -20.);

Отметим, что в новом языке С#, который поддерживается Studio .NET 7.0, такой прием является встроенным средством языка под названием indexer. С учетом сказанного введите следующую реализацию операции [ ]:

CDPointS CPolygon:: operator [](UINT i)
{
if (0 <= i && i < m_Points.size ())
return m_Points[i];
return m_ptLT;
}

Функция Set для установки обратного указателя может быть совмещена (overloaded) с одноименной функцией, позволяющей изменять атрибуты изображения полигона:

//====== Установка обратного указателя
void CPolygon::Set (CTreeDoc *p) { m_pDoc = p;
{
//====== Совмещенная версия для изменения атрибутов
void CPolygon::Set (CTreeDoc *p, COLORREF bCl, COLORREF pCl, UINT pen)
{
m_pDoc = p;
m_BrushColor= bCl;
m_PenColor = pCl;
m_nPenWidth = pen;
}

Деструктор класса должен освобождать память, занимаемую вложенным в объект контейнером точек:

CPolygon::~CPolygon()
{
m_Points.clear();
}
Если Вы заметили ошибку, выделите, пожалуйста, необходимый текст и нажмите CTRL + Enter, чтобы сообщить об этом редактору.