I’m trying to calculate the distance between two points. The two points I stored in a vector in C++: (0,0) and (1,1).
I’m supposed to get results as
0
1.4
1.4
0
But the actual result that I got is
0
1
-1
0
I think there’s something wrong with the way I use iterator in vector.
How can I fix this problem?
I posted the code below.
typedef struct point {
float x;
float y;
} point;
float distance(point *p1, point *p2)
{
return sqrt((p1->x - p2->x)*(p1->x - p2->x) +
(p1->y - p2->y)*(p1->y - p2->y));
}
int main()
{
vector <point> po;
point p1; p1.x = 0; p1.y = 0;
point p2; p2.x = 1; p2.y = 1;
po.push_back(p1);
po.push_back(p2);
vector <point>::iterator ii;
vector <point>::iterator jj;
for (ii = po.begin(); ii != po.end(); ii++)
{
for (jj = po.begin(); jj != po.end(); jj++)
{
cout << distance(ii,jj) << " ";
}
}
return 0;
}
That your code compiles at all is probably because you have a
using namespace stdsomewhere. (Otherwisevectorwould have to bestd::vector.) That’s something I would advise against and you have just provided a good case why:By accident, your call picks up
std::distance(), which takes two iterators and calculates the distance between them. Remove the using directive and prefix all standard library types withstd::and the compiler will tell you that you tried to pass avector <point>::iteratorwhere apoint*was required.To get a pointer to an object an iterator points to, you’d have to dereference the iterator – which gives a reference to the object – and take the address of the result:
&*ii.(Note that a pointer would perfectly fulfill all requirements for a
std::vectoriterator and some earlier implementations of the standard library indeed used pointers for that, which allowed you to treatstd::vectoriterators as pointers. But modern implementations use a special iterator class for that. I suppose the reason is that using a class allows overloading functions for pointers and iterators. Also, using pointers asstd::vectoriterators encourages mixing pointers and iterators, which will prevent the code to compile when you change your container.)But rather than doing this, I suggest you change your function so that it takes references instead (see this answer for why that’s a good idea anyway.) :
Note that the points are taken by
constreferences. This indicates to the caller that the function won’t change the points it is passed.Then you can call it like this:
distance(*ii,*jj).On a side note, this
is a C-ism unnecessary in C++. Just spell it
That would make problems if this
structdefinition ever was to parse from a C compiler (the code would have to refer tostruct pointthen, not simplypoint), but I guessstd::vectorand the like would be far more of a challenge to a C compiler anyway.