简体   繁体   中英

C++ Pointers/References

This code takes coordinates from mouse click and creates a new vertex;

void DrawingWidget::mousePressEvent(QMouseEvent *event){
   if(getCurrentState()==ADD_VERTEX){
      x=event->x();
      y=event->y();

      Vertex p1 {&x,&y};
      m_mainWindow->addVertex(p1);
      update();
   }
}

Here is Vertex class code:

class Vertex {

public:

   float *x = 0;
   float *y = 0;

   Vertex() = default;
   Vertex(float *nx, float *ny);
};

All Verces are held in list:

QList<Vector2> vertexList;

And addVertex(Vertex vertex):

addVertex(Vertex vertex){
   vertexList << vertex;
}

Basically first vertex adding works perfectly, but when I'm trying to add second vertex(using the given method), first vertex coordinates are changed instead.

NB! Coordinates of Vertex class are intentionally pointers, because by using another method I'm changing their coords.

What am I missing?

x and y in your code are probably fields of DrawingWidget and in Vertex you are storing pointers always to same variables (those fields). So in vertexList you have always the same values of pointers to the same fields.
I don't understand why you are surprised by your code behavior.

The code in your question and the behavior you observe implies you have something like this:

class DrawingWidget
{
public:
    void mousePressEvent(QMouseEvent *event);
private:
    float x;
    float y;
    // ...
};

And when the function mousePressEvent() is called, you're assigning the new coordinates to those members:

void DrawingWidget::mousePressEvent(QMouseEvent *event){
   if(getCurrentState()==ADD_VERTEX){
      x=event->x();
      y=event->y();
...

So everytime you press the mouse, you're overwriting the old coordinates. Now, this might have not been a problem, but since the Vertex s you add to the list contains pointers to those class members, instead of simply storing a copy of the coordinates, the first vertex appears to have changed coordinates.

The way to deal with this is to not use pointers at all (at least for your classes)!

class Vertex
{
public:
    Vertex() : x(0.0f), y(0.0f) {}
    Vertex(float x, float y) : x(x), y(y) {}

    float getX() const { return x; }
    float getY() const { return y; }

    void setX(float x) { this->x = x; }
    void setY(float y) { this->y = y; }

private:
   float x; // NOT pointers!
   float y;
};

class DrawingWidget
{
public:
    void mousePressEvent(QMouseEvent *event);
private:
    //float x; // Not needed!
    //float y;
    // ...
};

void DrawingWidget::mousePressEvent(QMouseEvent *event) {
   if(getCurrentState()==ADD_VERTEX) {
      Vertex p1{event->x(), event->y()};
      m_mainWindow->addVertex(p1);
      update();
   }
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM