Skip to content

Instantly share code, notes, and snippets.

@ttldtor
Created April 23, 2014 10:16
Show Gist options
  • Save ttldtor/11209741 to your computer and use it in GitHub Desktop.
Save ttldtor/11209741 to your computer and use it in GitHub Desktop.
#include <iostream>
#include <iomanip>
#include <fstream>
#include <vector>
#include <chrono>
#include <utility>
#include <cmath>
const size_t records_number = 1000000;
const size_t check_status_chunk_size = records_number / 100;
const size_t check_pass_chunk_size = records_number / 1000;
struct star_info
{
long x,y,z;
unsigned long long distance_square(const star_info& another_star_info) const
{
unsigned long long dx = x - another_star_info.x, dy = y - another_star_info.y, dz = z - another_star_info.z;
return dx * dx + dy * dy + dz * dz;
}
};
std::basic_istream<char>& operator>>(std::basic_istream<char>& is, star_info& str)
{
is >> str.x >> str.y >> str.z;
return is;
}
std::basic_ostream<char>& operator<<(std::basic_ostream<char>& is, const star_info& str)
{
is << "{" << str.x << "; " << str.y << "; " << str.z << "}";
return is;
}
template<class R, class T>
inline R duration(const T& time_point1,const T& time_point2)
{
auto d = std::chrono::duration_cast<std::chrono::duration<R>>(time_point2 - time_point1);
return d.count();
}
void print_loading_status(size_t percent)
{
std::cout << "\rLoading: " << std::setw(3) << percent << " %";
}
template<class F>
void load_data(std::ifstream& data, std::vector<star_info>& stars, F process_data)
{
auto t = std::chrono::high_resolution_clock::now();
size_t i = 0;
while (!data.eof() && i < records_number)
{
data >> stars[i];
++i;
if (i % check_status_chunk_size == 0)
{
print_loading_status(i * 100.0 / records_number);
}
}
std::cout << "\nDone! - " << duration<double>(t, std::chrono::high_resolution_clock::now()) << " sec" << std::endl << std::endl;
process_data();
}
auto main() -> int
{
auto t0 = std::chrono::high_resolution_clock::now();
std::ifstream data("stars.dat");
if (data.is_open())
{
std::vector<star_info> stars(records_number);
load_data(data, stars, [&]()
{
unsigned long long min_distance_square = (unsigned long long)-1;
size_t min_distance_square_star_indexes[2] = {0, 0};
auto t1 = std::chrono::high_resolution_clock::now();
auto t2 = t1;
for (size_t current = 0; current < stars.size() - 1; ++current)
{
for (size_t i = current + 1; i < stars.size(); ++i)
{
auto current_distance_square = stars[current].distance_square(stars[i]);
if (current_distance_square < min_distance_square)
{
min_distance_square = current_distance_square;
min_distance_square_star_indexes[0] = current;
min_distance_square_star_indexes[1] = i;
}
}
if ( current % check_pass_chunk_size == 0)
{
std::cout << "Pass # " << current <<" done - " << duration<double>(t2, std::chrono::high_resolution_clock::now()) << " sec" << std::endl;
t2 = std::chrono::high_resolution_clock::now();
}
}
std::cout << "\nAll passes done - " << duration<double>(t1, std::chrono::high_resolution_clock::now()) << " sec" << std::endl;
std::cout << "Minimal distance = " << pow(min_distance_square, 0.5) << std::endl;
std::cout << "Stars:{ID: " << min_distance_square_star_indexes[0] << ":" << stars[min_distance_square_star_indexes[0]] << "; ID: " << min_distance_square_star_indexes[1] << ":" << stars[min_distance_square_star_indexes[1]] << ")\n";
});
}
else
{
std::cout << "Can't open data file!" << std::endl;
}
std::cout << "Work done - " << duration<double>(t0, std::chrono::high_resolution_clock::now()) << " sec" << std::endl;
std::cin.get();
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment