carlosmay |
» 2017-12-05 21:47:04 Jeśli ma być tylko policzone ile jest powtarzających się liczb, można tak: #include <iostream> #include <algorithm> #include <iterator>
int main() { int arr[] { 1, 2, 3, 4, 5, 6, 7, 8, 9 }; int arr2[] { 2, 4, 6, 8, 10, 12, 14, 16 }; std::cout << std::count_if( std::begin( arr ), std::end( arr ), [ & ]( int el ) { return std::find( std::begin( arr2 ), std::end( arr2 ), el ) != std::end( arr2 ); } ); } Pisane z palca, ale powinno działać. |
|
grzeso Temat założony przez niniejszego użytkownika |
» 2017-12-05 21:47:20 Mam w jednym obiekcie jeden zbiór a w drugim obiekcie drugi zbiór i może da się to jakoś wykorzystać. W sensie porównać te obiekty czy coś (to tak w uproszczeniu pisze o porównaniu obiektów)
Chodzi mi o to że ktoś mi pokazywał jakąś konstrukcje bez użycia ifa i szukam inspiracji jak to odtworzyć
|
|
pekfos |
» 2017-12-05 22:17:18 carlosmay: to to samo co w pierwszym poście, tylko nie widać tych pętli. Chodzi o uniknięcie złożoności kwadratowej. ktoś mi pokazywał jakąś konstrukcje bez użycia ifa i szukam inspiracji jak to odtworzyć |
Może chodziło o ?:, różnica praktycznie tylko w zapisie. |
|
grzeso Temat założony przez niniejszego użytkownika |
» 2017-12-05 22:59:26 do carlosmay kod nie za bardzo działa moge poprosić o wyjaśnienie co to jest ten fragment: std::cout << std::count_if( std::begin( arr ), std::end( arr ), [ & ]( int el ) { return std::find( std::begin( arr2 ), std::end( arr2 ), el ) != std::end( arr2 ); }
a konkretnie : [ & ]( int el ) { return std::find( std::begin( arr2 ), std::end( arr2 ), el ) != std::end( arr2 ); }
bo od poczatku do kończa arr szuka tego co jest wyżej? czemu jest find to wiem, tylko find zwraca 1 element i jak to ma zadziałać na zasadzie przeszukania 2 zbiorów? |
|
carlosmay |
» 2017-12-05 23:28:06 Wyrażenia lambda (C++11)Funkcja count_if liczy wystąpienia tych elementów tablicy arr, dla których predykat zwraca true, czyli w tablicy arr2 znajdzie taką samą wartość. Wyrażenie lambda jest tutaj użyte w roli predykatu. Co nie działa? Daje wyniki niezgodne z oczekiwaniami, czy jest jakiś błąd kompilacji (włącz C++11). pekfos ma rację, co do złożoności. edit: wstawiam jeśli chce ci się analizować: dane pochodzą z dwóch plików, zawierających dokładnie 10000 liczb z przedziału 1 - 1000000. #include <iostream> #include <cstdlib> #include <string> #include <set> #include <unordered_set> #include <vector> #include <chrono> #include <algorithm> #include <iterator> #include <utility> #include <fstream> using namespace std;
template < typename C > size_t count_duplicate( const C & coll_1, const C & coll_2 ) { return count_if( begin( coll_1 ), end( coll_1 ), [ & ]( auto el ) { return coll_2.find( el ) != end( coll_2 ); } ); }
template < typename C > auto work_time_and_count_duplicate( const C & coll_1, const C & coll_2 ) { using tp = chrono::high_resolution_clock::time_point; tp start = chrono::high_resolution_clock::now(); size_t count = count_duplicate( coll_1, coll_2 ); tp stop = chrono::high_resolution_clock::now(); double diff = chrono::duration_cast < chrono::duration < double >>( stop - start ).count(); return make_pair( diff, count ); }
template < typename C > C create_coll( const string & path ) { C ret = C { }; ifstream fin( path ); if( fin ) { typename C::value_type val { }; while( fin >> val ) { ret.insert( val ); } } return ret; }
template < typename C > void print_arrays_state( const C & coll_1, const C & coll_2 ) { pair < double, size_t > count_set = work_time_and_count_duplicate( coll_1, coll_2 ); cout << "found " << count_set.second << " dupilactes in " << count_set.first << " sec\n"; }
template < typename C > void print_vector_state( const C & v1, const C & v2 ) { using hrc_tp = chrono::high_resolution_clock::time_point; hrc_tp start = chrono::high_resolution_clock::now(); size_t count = count_if( begin( v1 ), end( v1 ), [ & ]( auto el ) { return find( begin( v2 ), end( v2 ), el ) != end( v2 ); } ); hrc_tp stop = chrono::high_resolution_clock::now(); double diff = chrono::duration_cast < chrono::duration < double >>( stop - start ).count(); cout << "found " << count << " dupilactes in " << diff << " sec\n"; }
int main() { string path_1 { "test_1.txt" }; string path_2 { "test_2.txt" }; set < unsigned > s1 = create_coll < decltype( s1 ) >( path_1 ); set < unsigned > s2 = create_coll < decltype( s2 ) >( path_2 ); print_arrays_state( s1, s2 ); unordered_set < unsigned > us1 { begin( s1 ), end( s1 ) }; unordered_set < unsigned > us2 { begin( s2 ), end( s2 ) }; print_arrays_state( us1, us2 ); vector < unsigned > v1 { begin( s1 ), end( s1 ) }; vector < unsigned > v2 { begin( s2 ), end( s2 ) }; print_vector_state( v1, v2 ); cin.get(); return EXIT_SUCCESS; }
Czasy analizy dla dokładnie tych samych danych: pierwszy dla std::set drugi dla std::unordered_set trzeci dla tablicy std::vector found 108 dupilactes in 0.000521103 sec found 108 dupilactes in 0.000133919 sec found 108 dupilactes in 0.0478203 sec
|
|
RazzorFlame |
» 2017-12-06 13:48:39 template < typename C > auto work_time_and_count_duplicate( const C & coll_1, const C & coll_2 ) { using tp = chrono::high_resolution_clock::time_point; tp start = chrono::high_resolution_clock::now(); size_t count = count_duplicate( coll_1, coll_2 ); tp stop = chrono::high_resolution_clock::now(); double diff = chrono::duration_cast < chrono::duration < double >>( stop - start ).count(); return make_pair( diff, count ); }
Chyba tak będzie to wyglądać czytelniej: template < typename C > auto work_time_and_count_duplicate( const C & coll_1, const C & coll_2 ) { using hr_clock = chrono::high_resolution_clock; using seconds_d = chrono::duration < double >; auto start = hr_clock::now(); auto count = count_duplicate( coll_1, coll_2 ); auto stop = hr_clock::now(); auto diff = chrono::duration_cast < seconds_d >( stop - start ).count(); return make_pair( diff, count ); }
|
|
grzeso Temat założony przez niniejszego użytkownika |
» 2017-12-07 20:00:47 Dzięki wielkie za pomoc, zaraz sobie to wszystko przeanalizuje |
|
1 « 2 » |