Error: selecting temporary address [-fpermissive]

I considered this for several hours, but to no avail. I basically

struct rectangle { int x, y, w, h; }; rectangle player::RegionCoordinates() // Region Coord { rectangle temp; temp.x = colRegion.x + coordinates.x; temp.w = colRegion.w; temp.y = colRegion.y + coordinates.y; temp.h = colRegion.h; return temp; } // Collision detect function bool IsCollision (rectangle * r1, rectangle * r2) { if (r1->x < r2->x + r2->w && r1->x + r1->w > r2->x && r1->y < r2->y + r2->h && r1->y + r1->h > r2->y) { return true; } return false; } //blah blah main while loop if (IsCollision(&player1.RegionCoordinates(), &stick1.RegionCoordinates())) //ERROR { player1.score+=10; stick1.x = rand() % 600+1; stick1.y = rand() % 400+1; play_sample(pickup,128,128,1000,false); } 

Any ideas? I am sure that this is really obvious, but for life I can not understand.

+7
source share
3 answers

RegionCoordinates() returns an object by value. This means that calling RegionCoordinates() returns a temporary instance of the rectangle . As the error says, you are trying to accept the address of this temporary object, which is not legal in C ++.

Why is IsCollision() accepting pointers anyway? It would be natural to take its parameters from the const link:

 bool IsCollision (const rectangle &r1, const rectangle &r2) { if (r1.x < r2.x + r2.w && r1.x + r1.w > r2.x && r1.y < r2.y + r2.h && r1.y + r1.h > r2.y) { return true; } return false; } //blah blah main while loop if (IsCollision(player1.RegionCoordinates(), stick1.RegionCoordinates())) //no error any more { player1.score+=10; stick1.x = rand() % 600+1; stick1.y = rand() % 400+1; play_sample(pickup,128,128,1000,false); } 
+11
source

Since IsCollision accepts a rectangle * , and you take the address of the result here:

 if (IsCollision(&player1.RegionCoordinates(), &stick1.RegionCoordinates())) 

You are most likely returning the rectangle back from RegionCoordinates() , which is a temporary variable, since it will disappear after the if executed. If you assign the result of RegionCoordinates() variable, then it will cease to be temporary, and you can take its address:

 rectangle r1 = player1.RegionCoordinates() ; rectangle r2 = stick1.RegionCoordinates() ; if (IsCollision(&r1, &r2)) 

Alternatively, you can take parameters as const links, which will be more similar to C ++:

 bool IsCollision (const rectangle &r1, const rectangle &r2) 
+3
source

Given the type of error you are getting, I should assume that RegionCoordinates() returns the object by value, which causes the creation of a temporary one, and you take the address of that temporary one.

The address operator requires an lvalue as its operand, but you apply it to an rvalue (temporary values ​​are rvalues).

You can do this (if you are not using C ++ 11, replace auto with the type returned by RegionCoordinates ):

 auto rcPlayer1 = player1.RegionCoordinates(); auto rcStick1 = player1.RegionCoordinates(); if (IsCollision(&rcPlayer1, &rcStick1)) //ERROR { player1.score+=10; stick1.x = rand() % 600+1; stick1.y = rand() % 400+1; play_sample(pickup,128,128,1000,false); } 

Alternatively, you can change IsCollision so that it IsCollision links, not pointers, as Angel suggested in his answer .

+1
source

All Articles