Установка свойства readonly из другого класса

Предположим, у меня есть классы как:

namespace scope
{

class A
{
private:
int a;
public:
...
};

class B
{
public:
...
A method();
...
};

};

Определение метода:

A B::method()
{
A object;
object.a = 3;    // private member access error
// access via object (pointer) error if inheritance is used
return object;
}

Наиболее распространенный способ решения ошибки доступа — использование методов установки + получения.

Однако я не хочу устанавливать какие-либо другие области (или кто-то, использующий API) A.aтак метод публичного сеттера запрещен для этого случая.

a может быть публичным но он должен быть доступен только для чтения на стороне API. Так должно быть Чтение + запись на стороне источника, потому что, например, я хочу установить его с B::method, Как я могу добиться этого поведения?

Я пробовал наследование, а также дружеские отношения. Я также играл с immutable а также const декларации о недвижимости. Проблема в том, что когда я объявляю объект с конструктором по умолчанию, для свойства устанавливается какое-то значение, например -918316838410 (которое может возникнуть из-за того, что я не использую externЯ не уверен) и не может быть установлен method позже.

Любые идеи будут оценены. Заранее спасибо.

2

Решение

Вы хотите, чтобы B имел доступ к A, чего не хотите иметь другие люди?

Это дружба.

добавлять friend class Bв определение класса А, и все будет счастье.

Кстати, общие примеры для этого, когда я использую несколько классов для создания одного интерфейса. Например, такие вещи, как список<> и карта<> обычно нужны классы узлов, и эти классы часто хотят иметь доступ друг к другу. Это нарушение инкапсуляции прекрасно, так как с логической точки зрения это действительно один большой класс.

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

2

Другие решения

Как сказал Ричард, ты можешь использовать дружбу. Но имейте в виду, что когда вам нужна дружба, вы, вероятно, должны снова подумать о своем дизайне. Как сказал и Ричард, возможно, использование в качестве параметра конструктора A должно делать именно то, что вы хотите.

Вот рабочий пример с дружбой:

#include <iostream>
namespace scope
{
class A{
friend class B;
private:
int a;
public:
void print(){
std::cout << a << std::endl;
}
};

class B{
public:
A method(){
A a;
a.a=3;
return a;
}
};

int main(){
scope::B b;
scope::A a = b.method();
a.print(); //just to see it works...
}

Вот способ сделать то же самое без дружбы и частной жизни (хорошо, это уродливо 🙂

#include <iostream>
namespace scope
{
class B;
class A
{
private:
int a;
public:
void print(){
std::cout << a << std::endl;
}
// A way to only allow B instances to give a correct value
// of "a" member
void pleaseClassBSetMyPrivateMember(B& b);
};

class B
{
public:
A method(){
A a;
a.pleaseClassBSetMyPrivateMember(*this);
return a;
}

int computeValueForMemberOfClassA(A& a){
// you can access public members of a to
// calculate the proper value of a.a member
return 3;
}

};

void A::pleaseClassBSetMyPrivateMember(B& b)
{
// ask for class B object the correct value for member a
a = b.computeValueForMemberOfClassA(*this);
}

};
1

По вопросам рекламы [email protected]