### Need to calculate location distance between two vectors

I really need your help I started working with C++ for my project and I need to solve a problem . My problem is that I have a program that contains information about patient and Doctors in order to have an idea I ll give you a general structor of the project . So I created 3 classes :

Person : Attributes ( Id , Latitude , longitude ) ( Person.h & Person.cpp) Patient: Attributes ( state) ( Patient.h & Patient.cpp) it inherits from Person Doctor : Attributes (Id_Profession) (Doctor.h & doctor.cpp) it also inherits from class Person

The problem to create a function that calculate the distance between each patient and doctors : so I created the function below

 ``123456789101112131415161718192021222324252627282930`` ``````double Distance (const vector & Pat, const vector & Gen) { double dist; for (unsigned int i =0 ; i <10; i++) { for (unsigned int j =0; j< 10; j++) { dist= sin((Pat[i].GetLat())/180 * pi) *sin((Gen[j].GetLat())/180 * pi) + cos((Pat[i].GetLat())/180 * pi) * cos((Gen[j].GetLat())/180 * pi) * cos( (Pat[i].GetLong() - Gen[j].GetLong())/180 * pi); dist = acos(dist); dist = 6371 * dist; //j++; cout < myPat; vector myGen; fillGeneralist(myGen); //Function that fils my vector of doctors already defined fillPatient(myPat); Distance (myPat, myGen); return 0; }``````

could someone please help me the program returns all distances but I need to return distance between each patient and all doctors I need to have at the end the following results

The distance between patient 1 and doctor 1 is : ... The distance between patient 1 and doctor 2 is : ... The distance between patient 1 and doctor 3 is : ... .
.
. The distance between patient 10 and doctor 10 is : ...

Last edited on
 the program returns all distances

The first problem is that it doesn't.
So the problem I see is that you have your return statement within the for loops. This will cause Distance to return in the very first iteration, i = 0 and j = 0.
In other words, Distance function only calculates the distance between Pat[0] and Gen[0].
You need to compare every Pat[i] to every Gen[j], which is Pat.size() * Gen.size() operations.

What I would personally do is reformat your code a bit.
I would create a function that is just called
 ``123456789`` ``````double Distance(const Patient& pat, const Generalist& gen) { double dist= sin((pat.GetLat())/180 * pi) *sin((gen.GetLat())/180 * pi) + cos((pat.GetLat())/180 * pi) * cos((gen.GetLat())/180 * pi) * cos( (pat.GetLong() - gen.GetLong())/180 * pi); dist = acos(dist); dist = 6371 * dist; return dist; }``````

...and then, call the function like this:

 ``12345678`` ``````for (int i = 0; i < pat.size(); i++) { for (int j = 0; j < gen.size(); j++) { double dist = Distance(pat[i], gen[j]); std::cout << "The distance between patient" << i+1 << " and doctor " << j+1 << " is : " << dist << std::endl; } }``````
Last edited on
I'd certainly second @Ganado's recommendation to have a separate function, and call it with a nested loop of doctors and patients. However, it might be nice not to restrict its arguments to Patient and Doctor - you might want the distance between two doctors, for example, or the distance between patient and hospital.

So maybe a distance function that only depends on the (latitude,longitude) pairs:
 ``123456789101112131415`` ``````double distance( double latA, double longA, double latB, double longB ) // latitude and longitude of arbitrary entities { constexpr double degToRad = 3.14159265358979 / 180.0; // conversion factor, evaluated at compile time const double radEarth = 6371; // mean radius of the earth in km latA *= degToRad; // convert to radians (if originally in degrees) longA *= degToRad; latB *= degToRad; longB *= degToRad; double cosAngle = sin( latA ) * sin( latB ) + cos( latA ) * cos( latB ) * cos( longA - longB ); // cosine of angle between position vectors, from spherical coordinates and dot product return radEarth * acos( cosAngle ); // great-circle distance ( "r x theta" ) }``````

then called by
 ``12345678`` ``````for ( int i = 0; i < pat.size(); i++ ) { for ( int j = 0; j < gen.size(); j++ ) { double dist = distance( pat[i].GetLat(), pat[i].GetLong(), Gen[j].GetLat(), Gen[j].GetLong() ); cout << "The distance between patient" << i + 1 << " and doctor " << j + 1 << " is " << dist << "km " << endl; } }``````

Last edited on
+1 much cleaner
 ``1234567891011121314151617181920212223242526272829303132333435363738394041`` ``````#include #include struct location { int latitude = 0 ; int longitude = 0 ; }; double distance( location a, location b ) ; // TO DO struct person { unsigned int id ; location loc ; }; double distance( const person& a, const person& b ) { return distance( a.loc, b.loc ) ; } struct doctor : person { /* ... */ }; struct patient : person { /* ... */ }; struct distance_info // info about distances from one patient to many doctors { unsigned int patient_id ; // key: id of the doctor mapped value: distance from this patient std::map< unsigned int, double > distance_to_docs ; }; // return distance info for distance from one patient to each doctors distance_info distances( const patient& p, const std::vector& docs ) { distance_info di { p.id, {} } ; for( const doctor& d : docs ) di.distance_to_docs.emplace( d.id, distance(p,d) ) ; return di ; } // return distance info for all patients to all doctors std::map< unsigned int, distance_info > // key: patient id mapped value: distance info distances( const std::vector& patients, const std::vector& docs ) { std::map< unsigned int, distance_info > di_all ; for( const patient& p : patients ) di_all.emplace( p.id, distances( p, docs ) ) ; return di_all ; }``````
Hello

I want to thank you a lot for your help, I tried @Ganado and @lastchance suggestion and it works well.

@JLBorges thank you also for your help

Last edited on