C++ - Initialize private array in c++ class - c++

I'm having a problem of storing data into the private array in a class.
I tried to Google and didn't find any solution.
Here's my code:
Foo.h
class Foo {
private:
int arr[10];
double d;
public:
Foo::Foo(double d) {
this->d = d;
}
// ...
};
Foo.cpp
int main() {
double d = 123.456;
int array[10];
// Getting data from user input by for-loop 10 times.
Foo f = Foo(d);
And here's my problem -- how to save the array into the f?
Seems like using pointer (*f.arr = array;) doesn't acturally change the arr.
I tried this solution by adding
class Foo {
// ...
Public:
Foo::Foo(int arr_, double d_) : arr_(new int[10]), d_(d) { };
But the Visual Studio 2017 says the array is not initialized.
I also tried this solution, but VS says cannot modify the array in this scope.
Please help. Thank you in advance.

#include <algorithm> // std::copy()
#include <iterator> // std::size()
class Foo {
private:
int arr[10];
double d;
public:
Foo(double d, int *data)
: d{ d }
{
std::copy(data, data + std::size(arr), arr);
}
// ...
};

Related

Access to a private variable in a C++ class that contains an array of structures

I am writing a C++ class that will contain an array of structures.
typedef struct
{
int a;
int b;
std:string c;
} MyElementType;
class MyClass
{
private:
MyElementType myElement1;
std::vector <MyElementType> myElementVector1;
public:
MyElementType myElement2;
std::vector <MyElementType> myElementVector2;
MyClass();
~MyClass();
void addMyElement1 (int, int, std::string);
// Other methods.
};
I need to insert objects of type MyElementType into the vector From main.
I can insert elements into the vector myElementVector2 like this:
int main ()
{
MyClass myClassObj;
myClassObj.myElement2.a = 2;
myClassObj.myElement2.b = 20;
myClassObj.myElement2.c = "text2";
myClassObj. myElementVector2.push_back(myClassObj.myElement2);
}
To do the same with myElementVector1 I must call the public method defined in the MyClass class:
myClassObj.addMyElement1 (1, 10, "text1");
Having defined the addMyElement1 method like so:
void MyClass::addMyElement1 (int la, int lb, std::string lc)
{
MyElementType lmyElement1;
lmyElement1.a = la;
lmyElement1.b = lb;
lmyElement1.c = lc;
myElementVector1.push_back(lmyElement1);
};
This example is very simple, but in the real program the MyElementType structure has more than twenty fields and some of them are a vector instead of a simple data type. Something similar to this:
typedef struct
{
int ID;
std:string NAME;
} MyElementType2;
typedef struct
{
int a;
int b;
std:string c;
vector <MyElementType2> v;
} MyElementType;
To insert objects into myElementVector2 you would need a public function that receives all these parameters, creates myElement1 and inserts it into myElementVector1
It could be something like this, but I don't know how to pass the parameter with the vector v (which will contain several objects of type MyElementType2) and have all that added to myElementVector1
void MyClass::addMyElement1 (int la, int lb, std::string lc, ¿ VECTOR_PARAM ?)
{
MyElementType myElement1;
myElement1.a = la;
myElement1.b = lb;
myElement1.c = lc;
¿ myElement1.v = VECTOR_PARAM; ?
myElementVector1.push_back(myElement1);
};
Any suggestions or help are appreciated as I haven't found any information on this.

C++ ,Single Inheritance, Garbage Value

#include<iostream>
using namespace std;
class Alpha
{
int a;
public:
void get_a(int x)
{
a = x;
}
int hello()
{
return a;
}
};
class Beta : public Alpha
{
int b, c;
public:
void get_b(int y)
{
b = y;
}
void add()
{
c = hello() + b;
cout << c << endl; // displays garbage value
}
};
int main()
{
Alpha v1;
Beta v2;
v1.get_a(4);
v2.get_b(3);
v2.add();
v2.disp();
return 0;
}
The output of v2.disp() shows garbage value but when I initalise "a" as v2.get_a instead of v1.get_a , it shows the correct answer. New to C++ btw. Please help. Thanks.
The problem is that you have two different objects that are unrelated to each other. The object v1 is unrelated to the object v2, they are separate and distinct objects. You initialize Alpha::a with v1.get_a(4), that doesn't initialize Beta::a.
A solution to your problem is to use one object:
Beta v;
v.get_a(4);
v.get_b(3);
v.add();
v.disp();

C++ class member not initialized (at constructor, but does at initialize method)

I have a C++ class with two constructors (a default one and another with arguments). In order to reuse code, I avoided initializing class members at the constructor level, and I'm doing it in an Initialize method instead, which I am calling from both constructors. This way, I was hopping to minimize code lines and repeated code:
Location::Location(){
double pos[POSITION_SIZE] = {0};
this->Initialize(const_cast<char*>(""), const_cast<char*>(""), pos);
}
Location::Location(char *id, char *code, double pos[POSITION_SIZE]){
this->Initialize(id, code, pos);
}
void Location::Initialize(char *id, char *code, double pos[POSITION_SIZE]){
strcpy(this->ID, id);
strcpy(this->code, code);
this->position[0] = pos[0];
this->position[1] = pos[1];
this->position[2] = pos[2];
this->attribute1 = 0;
this->attribute2 = 0;
}
header:
class Location{
public:
Location();
Location(char *id, char *code, double pos[POSITION_SIZE]);
private:
// This method initializes the location attributes given as parameters
void Initialize(char *id, char *code, double pos[POSITION_SIZE]);
// Name/identifier of the location
char ID[ID_LENGTH];
// FIR identifier
char code[ID_LENGTH];
// Location's coordinates (lat, lon, alt)
double position[POSITION_SIZE];
// Attribute 1
double attribute1;
// Attribute 2
double attribute2;
};
I know that using initialize methods is a bad praxis when used because old school coding style or avoiding the usage of exceptions at constructor for example. But my goal here was reducing code, so unless some guru of stackoverflow says the opposite, I think it is not wrong (but I'm here to learn, so please destroy all my convictions).
The problem is that I'm getting a warning for not initializing class members within the cosntructor. The compiler doesn't like them to get initialized at the Initialize method. So, any way of making the compiler happy? Should I forget aboput Initialize method usage?
I would use constructor delegation, something like:
#include <iostream>
using namespace std;
class foo
{
public:
foo()
: foo(1, "2", 3.) // delegate to the other constructor with defaults...
{ }
foo(int a, std::string b, double c)
: _a(a), _b(b), _c(c)
{ }
private:
int _a;
std::string _b;
double _c;
};
int main() {
foo f1{};
foo f2{1, "3", 4.};
return 0;
}
With the caveat that you can use atleast c++11...

Name hiding from inherited classes

I have the following sample code and I wanted to know the correct way to get access to the Pass method in the CBar class. Currently I have found 3 ways to get access to this method and they are as follows:
Casting the object, ((CBar *) &foo)->Pass(1, 2, 3);
Using this syntax, foo.CBar::Pass(1,2,3);
Use the "using" syntax in the CFoo class declaration, using CBar::Pass.
The following is an example of a simple project to test this capability.
Foo.h
#include "bar.h"
class CFoo :
public CBar
{
private:
double m_a;
double m_b;
public:
CFoo(void);
~CFoo(void);
void Pass(double a, double b);
};
Foo.cpp
#include "Foo.h"
CFoo::CFoo(void)
{
m_a = 0.0;
m_b = 0.0;
}
CFoo::~CFoo(void)
{
}
void CFoo::Pass(double a, double b)
{
m_a = a;
m_b = b;
}
Bar.h
class CBar
{
int m_x;
int m_y;
int m_z;
public:
CBar(void);
~CBar(void);
void Pass(int x, int y, int z);
};
Bar.cpp
#include "Bar.h"
CBar::CBar(void)
{
m_x = 0;
m_y = 0;
m_z = 0;
}
CBar::~CBar(void)
{
}
void CBar::Pass(int x, int y, int z)
{
m_x = x;
m_y = y;
m_z = z;
}
And my main class DoStuff.cpp
#include "DoStuff.h"
#include "Foo.h"
CDoStuff::CDoStuff(void)
{
}
CDoStuff::~CDoStuff(void)
{
}
int main()
{
CFoo foo, foo1, foo2;
//This only gets to the Pass method in Foo.
foo.Pass(2.5, 3.5);
//Gets access to Pass method in Bar.
foo1.CBar::Pass(5,10,15);
//Can also case and access by location for the same result??
((CBar *) &foo2)->Pass(100,200,300);
return 0;
}
Are each of these options viable? Are some preferred? Are there pitfalls with using any one of the methods listed?
I am especially curious about the foo.CBar::Pass(1,2,3) syntax.
Thanks,
B
In this specific example all methods ultimately produce the same outcome.
In general case the outcomes might be different.
The "cast" method ((CBar *) &foo)->Pass(1, 2, 3); will preserve the dynamic nature of the call if Pass happens to be a virtual function. The cast can be performed in terms of reference type, BTW, ((CBar &) foo).Pass(1, 2, 3);. And using C++ style casts is a better idea in such situations.
The "qualified name" method foo.CBar::Pass(1,2,3); will suppress the dynamic nature of the call if Pass happens to be a virtual function, i.e. it is guaranteed to call CBar::Pass.

Multidimensional array assignment

if you look at this class, how do I achieve the following:
class foo {
public:
void foo(double (&arr)[3][4]) { //Constructor
arr2 = arr; //??? How to assign multidimensional arrays?
}
void bar() { //Usage
double doSomething = arr2[1][0];
}
private:
double* arr2[3][4]; //??? How to store this?
}
Thanks everyone!
More explanation: This should be a class, that get a reference to a two-dimensional array in its constructor (foo()). It stores this reference in a member variable, so that some other function (bar()) can access them later.
So what "format" has the member variable and how do I assign the parameter of the constructor to it?
Edit2: As I impement an interface, I can't change signatures to use std::vector>...
class foo {
public:
// See http://cdecl.ridiculousfish.com/?q=double+%28%26arr%29%5B3%5D%5B4%5D
foo(double (&arr)[3][4]) :arr2(&arr) {
// This constructor uses constructor list initialization, but you could have used
// assignment instead, like this:
// arr2 = &arr;
}
double bar() { //Usage
double doSomething = (*arr2)[1][0];
return doSomething*doSomething;
}
private:
// See http://cdecl.ridiculousfish.com/?q=double+%28*arr2%29%5B3%5D%5B4%5D
double (*arr2)[3][4];
};
int main () {
double oof[3][4] = {{0.,},};
foo moo(oof);
return int(moo.bar());
}
Since you don't specify a reason for using raw pointers and this is tagged C++, you should use nested vectors instead:
#include <vector>
class foo
{
public:
void foo(const std::vector<std::vector<double>>& arr)
: arr2(arr)
{ //Constructor
}
void bar() { //Usage
double doSomething = arr2[1][0];
}
private:
std::vector<std::vector<double>> arr2;
};