doubt on pointer array

M

marcofuics

Hi
I have the code:
££££££££££££££

#include <iostream>
using namespace std;



class CSquare
{
public:
double Side;

CSquare() : Side(0.00) {}
CSquare(double side) : Side(side) { }
~CSquare() { }

double getSide() const { return Side; }
void setSide(const double s)
{
if( s <= 0 )
Side = 0.00;
else
Side = s;
}

double Perimeter() { return Side * 4; }
double Area() { return Side * Side; }
};

class Container
{
public:
int counter;
CSquare* arr[1];
Container() : counter(0) {}

void add(CSquare* elm) {

arr[counter] = elm;
counter++;
}
};


int main()
{
CSquare *sqr[1];
Container container;
sqr[0] = new CSquare;
sqr[0]->setSide(1.0);
sqr[1] = new CSquare;
sqr[1]->setSide(2.0);
sqr[2] = new CSquare;
sqr[2]->setSide(3.0);
sqr[3] = new CSquare;
sqr[3]->setSide(4.0);

container.add(sqr[0]);
container.add(sqr[1]);


cout << "Squares Characteristics" << endl;
cout << "Square 0" << endl;
cout << "Side: " << sqr[0]->getSide() << endl;
cout << "Perimeter: " << sqr[0]->Perimeter() << endl;
cout << "Area: " << sqr[0]->Area() << endl;

cout << "Square 1" << endl;
cout << "Side: " << sqr[1]->getSide() << endl;
cout << "Perimeter: " << sqr[1]->Perimeter() << endl;
cout << "Area: " << sqr[1]->Area() << endl;

cout << "Square 2" << endl;
cout << "Side: " << sqr[2]->getSide() << endl;
cout << "Perimeter: " << sqr[2]->Perimeter() << endl;
cout << "Area: " << sqr[2]->Area() << endl;

cout << "Square 3" << endl;
cout << "Side: " << sqr[3]->getSide() << endl;
cout << "Perimeter: " << sqr[3]->Perimeter() << endl;
cout << "Area: " << sqr[3]->Area() << endl;

return 0;
}
££££££££££££££



and I thought that it should generate an error, instead I get this output




@@@@@@@@@@@@@@@@

Squares Characteristics
Square 0
Side: 2
Perimeter: 8
Area: 4
Square 1
Side: 2
Perimeter: 8
Area: 4
Square 2
Side: 3
Perimeter: 12
Area: 9
Square 3
Side: 4
Perimeter: 16
Area: 16

@@@@@@@@@@@@@@@@


why the first 2 elements give me the same result?
 
V

Victor Bazarov

I have the code:
££££££££££££££

#include <iostream>
using namespace std;



class CSquare
{
public:
double Side;

CSquare() : Side(0.00) {}
CSquare(double side) : Side(side) { }
~CSquare() { }

double getSide() const { return Side; }
void setSide(const double s)
{
if( s <= 0 )
Side = 0.00;
else
Side = s;
}

double Perimeter() { return Side * 4; }
double Area() { return Side * Side; }
};

class Container
{
public:
int counter;
CSquare* arr[1];

*One* element in that array.
Container() : counter(0) {}

void add(CSquare* elm) {

arr[counter] = elm;
counter++;

As soon as you advance 'counter' past 0, you can't use it to index in
the array of 1 element.
}
};


int main()
{
CSquare *sqr[1];

An array of *one* pointer to CSquare.
Container container;
sqr[0] = new CSquare;
sqr[0]->setSide(1.0);

OK so far.
sqr[1] = new CSquare;

BOOM!!!! Undefined behavior - you can't use 'sqr[1]' because it does
not exist. In order to use any index past 0, you need to define the
array to have the number of elements more than the largest index you
want to use.

Your program has *undefined behavior*. Read up on that.
sqr[1]->setSide(2.0);
sqr[2] = new CSquare;
sqr[2]->setSide(3.0);
sqr[3] = new CSquare;
sqr[3]->setSide(4.0);

container.add(sqr[0]);
container.add(sqr[1]);


cout << "Squares Characteristics" << endl;
cout << "Square 0" << endl;
cout << "Side: " << sqr[0]->getSide() << endl;
cout << "Perimeter: " << sqr[0]->Perimeter() << endl;
cout << "Area: " << sqr[0]->Area() << endl;

cout << "Square 1" << endl;
cout << "Side: " << sqr[1]->getSide() << endl;
cout << "Perimeter: " << sqr[1]->Perimeter() << endl;
cout << "Area: " << sqr[1]->Area() << endl;

cout << "Square 2" << endl;
cout << "Side: " << sqr[2]->getSide() << endl;
cout << "Perimeter: " << sqr[2]->Perimeter() << endl;
cout << "Area: " << sqr[2]->Area() << endl;

cout << "Square 3" << endl;
cout << "Side: " << sqr[3]->getSide() << endl;
cout << "Perimeter: " << sqr[3]->Perimeter() << endl;
cout << "Area: " << sqr[3]->Area() << endl;

return 0;
}
££££££££££££££



and I thought that it should generate an error, instead I get this output

Hint: undefined behavior means that no definite outcome is to be expected.
@@@@@@@@@@@@@@@@

Squares Characteristics
Square 0
Side: 2
Perimeter: 8
Area: 4
Square 1
Side: 2
Perimeter: 8
Area: 4
Square 2
Side: 3
Perimeter: 12
Area: 9
Square 3
Side: 4
Perimeter: 16
Area: 16

@@@@@@@@@@@@@@@@


why the first 2 elements give me the same result?

There is no explanation based on the language specification. Anything
can happen.

V
 
M

marcofuics

Il giorno martedì 1 aprile 2014 16:56:52 UTC+2, Victor Bazarov ha scritto:
BOOM!!!! Undefined behavior - you can't use 'sqr[1]' because it does

not exist. In order to use any index past 0, you need to define the

array to have the number of elements more than the largest index you

want to use.



Your program has *undefined behavior*. Read up on that.

ok ok
and this was also my thought....but
if you notice ... after the first element of the array then all goes well
 
M

marcofuics

maybe I was wrong to post an example derived from the original. Here is theoriginal below




££££££££££££££££££££££££££££££££££££

class SHMeasuresParameters;


class SetReceiver_SH
{
SHMeasuresParameters* _MeasureModes[1];
int _MeasureModesCounter;
void addMeasureModes(SHMeasuresParameters *element);
void removeMeasureModes(SHMeasuresParameters *element);
};



void SetReceiver_SH::addMeasureModes(SHMeasuresParameters *element)
{
_MeasureModes[_MeasureModesCounter] = element;
_MeasureModesCounter++;
}


void SetReceiver_SH::removeMeasureModes(SHMeasuresParameters *element)
{
int index = _MeasureModesCounter;
for(int i = 0; i < _MeasureModesCounter; i++)
{
if(_MeasureModes == element)
{
index = i;
break;
}
}
for(int i = index; i < _MeasureModesCounter - 1; i++)
{
_MeasureModes = _MeasureModes[i + 1];
}
_MeasureModesCounter--;
}
££££££££££££££££££££££££££££££££££££
 
V

Victor Bazarov

Il giorno martedì 1 aprile 2014 16:56:52 UTC+2, Victor Bazarov ha scritto:
BOOM!!!! Undefined behavior - you can't use 'sqr[1]' because it does

not exist. In order to use any index past 0, you need to define the

array to have the number of elements more than the largest index you

want to use.



Your program has *undefined behavior*. Read up on that.

ok ok
and this was also my thought....but
if you notice ... after the first element of the array then all goes well

There can be no "but". Undefined behavior is just that. You are lulled
into thinking that "all goes well", yet you're stomping all over the
memory that doesn't belong to the array to which you're supposedly
writing. That's the very same backdoor through which crackers can gain
access to computer systems and steal vital information or take control
of the computer in some other way. Hopefully you don't try to ship this
code to any unsuspecting customers.

V
 
I

Ian Collins

maybe I was wrong to post an example derived from the original. Here is the original below

££££££££££££££££££££££££££££££££££££

class SHMeasuresParameters;


class SetReceiver_SH
{
SHMeasuresParameters* _MeasureModes[1];

You still only have an array of 1 element.....
int _MeasureModesCounter;
void addMeasureModes(SHMeasuresParameters *element);
void removeMeasureModes(SHMeasuresParameters *element);
};



void SetReceiver_SH::addMeasureModes(SHMeasuresParameters *element)
{
_MeasureModes[_MeasureModesCounter] = element;

.....which you overflow.
 
B

Barry Schwarz

maybe I was wrong to post an example derived from the original. Here is the original below




££££££££££££££££££££££££££££££££££££

class SHMeasuresParameters;


class SetReceiver_SH
{
SHMeasuresParameters* _MeasureModes[1];
int _MeasureModesCounter;
void addMeasureModes(SHMeasuresParameters *element);
void removeMeasureModes(SHMeasuresParameters *element);
};



void SetReceiver_SH::addMeasureModes(SHMeasuresParameters *element)
{
_MeasureModes[_MeasureModesCounter] = element;
_MeasureModesCounter++;
}


void SetReceiver_SH::removeMeasureModes(SHMeasuresParameters *element)
{
int index = _MeasureModesCounter;
for(int i = 0; i < _MeasureModesCounter; i++)
{
if(_MeasureModes == element)
{
index = i;
break;
}
}
for(int i = index; i < _MeasureModesCounter - 1; i++)
{
_MeasureModes = _MeasureModes[i + 1];
}
_MeasureModesCounter--;
}
££££££££££££££££££££££££££££££££££££


This has the same problem as your original post. _MeasureModes is an
array with exactly one element. This element is _MeasureModes[0]. Any
expression that uses _MeasureModes with a subscript greater than 0
invokes undefined behavior.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,744
Messages
2,569,483
Members
44,903
Latest member
orderPeak8CBDGummies

Latest Threads

Top