Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Changing Struct or Class inside a Class | with or without pointers

Changing values of classes/structs inside classes are a mystery to me. I tried to do some research today and came up with the following solution. I wonder if this is a proper way for a function to change stuff inside the class. Is there a need to for this to be somehow done with pointers? Is there a more proper way to accomplish this?

#include <iostream>

int main()
{

class Someclass {
    private:
    int Integer;

    public:

    Someclass(int i):
    Integer(i){} //CTOR

    struct Somestruct { 
        int a, b;
    };
    Somestruct Mystruct;

    void func(){
        Mystruct.a = Integer/2;
        Mystruct.b = Integer*2;
    };
};

Someclass A(10);
A.func();
std::cout << A.Mystruct.a << " " << A.Mystruct.b << std::endl;
} 

The reason I am writing this code, is because I want to parse a file, starting from the line "Integer" into a customly defined struct "Mystruct" which this class should somehow deliver me. Is this an acceptable way to write such a code?

like image 586
Sadikov Avatar asked Aug 03 '26 02:08

Sadikov


2 Answers

I understand that your question is about encapsulation, being understood that the inner struct is a data holder and the outer class has to manage it somehow.

Weaknesses of your design

In your design, Mystruct is public. So anything outside Someclass could access the data, but also change it. This is error prone, as there is no guarantee that the outside code doesn't break some invariant of the structure.

Ways for improvement

The cleanest thing would certainly to make some getters and setters to access the data. But with 30 members, it's a lot of code.

If your construction process initialises the struture's data, a second approach could be to limit outside access to read-only. You'd do that by making Mystruct private and offering a function returning a const reference:

class Someclass {
    Somestruct Mystruct; 
public: 
    ...
    const Somestruct& get() { return Mystruct; }
};

std::cout << A.get().a << " " << A.get().b << std::endl;

Online demo

Nevertheless before going into that direction, I'd check if access to the structure's raw data couldn't be encapsulated, for example by providing functions that manage the data without need to know the internals:

class Somestruct {
    ...
public:
    ostream& show_simplified_specs(ostream& os) {
        os << a << " " << b;
    }
}

A third approach could be to use the builder design pattern to encapsulate the construction process of a Someclass based on Somestruct and other parts.

Pointers ?

Pointers should be avoided if possible. For example, suppose you have a vector of Someclass to keep all these classes in memory. At a moment in time, you get a pointer to an element's Mystruct. Suppose you'd then add a new item to the vector: all the previous pointers might get invalidated.

This same risk potentially exist with references. But I think that while it's a common idiom to cache a pointer returned by a function,in practice it's less common and appealing to copy a reference returned by a function.

like image 113
Christophe Avatar answered Aug 04 '26 14:08

Christophe


Is this what you're looking for? I'm not much confident I understood you right.

template <int I>
struct Someclass;

template <>
struct Someclass<1>
{
    int Integer = 1;
    int a, b;

    void func()
    {
        a = Integer/2;
        b = Integer*2;
    }
};

template <>
struct Someclass<2>
{
    int Integer = 2;
    int a, b, c;

    void func()
    {
        a = Integer/2;
        b = Integer*2;
        c = Integer*Integer;
    }
};

int main()
{
    Someclass<1> A;
    A.func();
    std::cout << A.a << " " << A.b << std::endl;

    Someclass<2> B;
    B.func();
    std::cout << B.a << " " << B.b << " " << B.c << std::endl;

    return 0;
}
like image 33
NuPagadi Avatar answered Aug 04 '26 15:08

NuPagadi