LINUX.ORG.RU

Stroustrup 10.2.4 Статические члены

 ,


0

1

Шото туплю. Почему конструктор имеет доступ к закрытым членам default_date?

class Date
{
int d,m,y;
public:
static Date default_date;
Date(int dd=0, int mm=0, int yy=0);
static void set_default(int,int,int);
};
Date::Date(int dd, int mm, int yy)
{
d=dd?dd:default_date.d;
m=mm?mm:default_date.m;
y=yy?yy:default_date.y;
}

Потому что default_date имеет тот же тип, что и класс, из которого выполняется обращение. «Приватный» не значит ограничение доступа из кода «к приватным полям только своего объекта», это скорее «к приватным полям любого объекта этого же класса (включая производные)».

xaizek ★★★★★
()

Почему конструктор имеет доступ к закрытым членам default_date?

потому-что любой метод из Date имеет доступ к любому полю Date.

Вот НЕ из Date к приватным членам нет доступа. В данном случае коструктор Date внутри Date, и потому он имеет доступ к полям d,m,y. А статичность не играет никакой роли.

emulek
()
Ответ на: комментарий от emulek

кстати, а почему default_date публичное? Оно тоже должно быть приватное ИМХО. Да и функция set_default(int,int,int); какая-то... Лишняя ИМХО.

emulek
()
class MoonCal
{
int d;
};

class SunCal
{
int d;
static SunCal default_sun;
static MoonCal default_moon;

public:
void Set(int d)
{
default_sun.d = d;  //A
default_moon.d = d; //B
}
};

Вот в таком виде выглядит нелогично.

deathmokar
() автор топика
Ответ на: комментарий от Gvidon

Я знаю что говорит компилятор, я знаю что написано у страуструпа. Нелогичность в следующем. В классе SunCal два логически эквивалентных статических члена, но к закрытой части одного из них есть доступ только через его интерфейс, а к закрытой части другого - минуя его интерфейс.

deathmokar
() автор топика
Ответ на: комментарий от deathmokar

два логически эквивалентных

Компилятору плевать на твою логическую эквивалентность, у него нет такого понятия. Для него MoonCal и SunCal - это разные сущности, у которых нет ничего общего. Хочешь получить доступ из одного класса к закрытым членам другого - объяви его другом, для этого этот механизм и существует.

Gvidon ★★★★
()
Ответ на: комментарий от Gvidon

Ты не с той стороны смотришь. Не нужно получать доступ к закрытой части другого класса //B.

class MoonCal {
 int d;
public:
int getd(){return d;}
 }; 
class SunCal { 
int d;
 static SunCal default_sun; 
static MoonCal default_moon; 
public: 
int getd(){return d;}
void print() { 
std::cout<<default_sun.getd();
std::cout<<default_moon.getd();
std::cout<<default_sun.d;
 } 
};

Последний вывод переступает через интерфейс getd (что если он крайне не тривиален).

deathmokar
() автор топика
Ответ на: комментарий от deathmokar

Последний вывод переступает через интерфейс getd (что если он крайне не тривиален).

Через что он переступает, прошу прощения?

void SunCal::print(); — метод (экземпляра) класса SunCal. default_sun — экземпляр класса SunCal. Любой метод класса SunCal будет иметь доступ к любому закрытому полю любого экземпляра класса SunCal.

Чтобы было проще понять: защиты от доступа одного экземпляра класса к закрытому полю другого экземпляра того же класса нет.

theNamelessOne ★★★★★
()
Ответ на: комментарий от deathmokar

Я всё ещё не понимаю, что тебе не нравится. Возможно, я слишком много времени провёл с плюсовым кодом, и теперь мне всё это кажется абсолютно очевидным и элементарным, но, блин, я не понимаю, что с этим кодом не так. Всё понятно и логично. Есть private поля, доступ к ним имеет только этот же класс и его друзья. Заметь, абсолютно любой метод класса имеет доступ ко всем его закрытым полям. Есть публичные поля, доступ к ним имеет кто угодно. Вполне понятная идея

Gvidon ★★★★
()
Ответ на: комментарий от theNamelessOne

Всё, мозг стал на место. Спасибо доктор.

deathmokar
() автор топика
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.