Jump to content

So i'm curious is there a better way to sort many variables at the time when they are in a STRUCT.

If we have:

struct glove{    int sex;//  3 = male, 4 - female    int hand;// 1 - left , 2 - right    int size;};

and i'd like to sort by the sex, so that first would be all the males  ( 3 ), and then the females ( 4 ).

3 1 42 3 1 25 3 1 36 3 2 254 1 25 4 1 13 4 2 15 4 2 25 

so that i would not need to wrtite this:

for(int i=0; i<n-1; i++)    {        for(int j=1; j<n; j++)        {            if(p[i].sex>p[j].sex)            {                int num = p[i].sex;//THIS                p[i].sex=p[j].sex;//PART                p[j].sex=num;// HERE            }        }    }

for three times, is there a way to move all three elements at the same time?

i5-4690k, R9 380 4gb, 8gb-1600MHz ram, corsair vs 550w, astrock h97m anniversary.

 

Link to comment
https://linustechtips.com/topic/468707-sort-arrays-c/
Share on other sites

Link to post
Share on other sites

You're using what is known as bubble sort. There are way more efficient methods, but none is shorter to write.

 

For example you could use quick sort:

void quicksort(int *arr, int left, int right){    int min = (left+right)/2;    cout<<"QS:"<<left<<","<<right<<"\n";    int i = left;    int j = right;    int pivot = arr[min];    while(left<j || i<right)    {        while(arr[i]<pivot)        i++;        while(arr[j]>pivot)        j--;        if(i<=j){            swap(i,j,arr);            i++;            j--;        }        else{            if(left<j)                quicksort(arr, left, j);            if(i<right)                quicksort(arr,i,right);            return;        }    }}

Don't ask to ask, just ask... please 🤨

sudo chmod -R 000 /*

Link to comment
https://linustechtips.com/topic/468707-sort-arrays-c/#findComment-6286755
Share on other sites

Link to post
Share on other sites

http://linustechtips.com/main/topic/422629-sorting-algorithms/

A thread of mine. The techniques can be easily implemented using templates.

Or use std::vector and its sorting algorithm which can be use a custom function.

 

STL ftw.

i5 4670k @ 4.2GHz (Coolermaster Hyper 212 Evo); ASrock Z87 EXTREME4; 8GB Kingston HyperX Beast DDR3 RAM @ 2133MHz; Asus DirectCU GTX 560; Super Flower Golden King 550 Platinum PSU;1TB Seagate Barracuda;Corsair 200r case. 

Link to comment
https://linustechtips.com/topic/468707-sort-arrays-c/#findComment-6286771
Share on other sites

Link to post
Share on other sites

 

You're using what is known as bubble sort. There are way more efficient methods, but none is shorter to write.

 

For example you could use quick sort:

void quicksort(int *arr, int left, int right){    int min = (left+right)/2;    cout<<"QS:"<<left<<","<<right<<"\n";    int i = left;    int j = right;    int pivot = arr[min];    while(left<j || i<right)    {        while(arr[i]<pivot)        i++;        while(arr[j]>pivot)        j--;        if(i<=j){            swap(i,j,arr);            i++;            j--;        }        else{            if(left<j)                quicksort(arr, left, j);            if(i<right)                quicksort(arr,i,right);            return;        }    }}

i dont really need other way to sort right now, just if i can sort 3 elements at the time

i5-4690k, R9 380 4gb, 8gb-1600MHz ram, corsair vs 550w, astrock h97m anniversary.

 

Link to comment
https://linustechtips.com/topic/468707-sort-arrays-c/#findComment-6286773
Share on other sites

Link to post
Share on other sites

i dont really need other way to sort right now, just if i can sort 3 elements at the time

 

no, because you can't know which elements are larger than the others before checking. @Nineshadow explains it pretty well, you'll see that there's no way you can make your code any shorter than that (why would you want to anyway?)

Don't ask to ask, just ask... please 🤨

sudo chmod -R 000 /*

Link to comment
https://linustechtips.com/topic/468707-sort-arrays-c/#findComment-6286793
Share on other sites

Link to post
Share on other sites

no, because you can't know which elements are larger than the others before checking. @Nineshadow explains it pretty well, you'll see that there's no way you can make your code any shorter than that (why would you want to anyway?)

i hoped there was a way to to avoid writing this:

int num = p[i].sex;//THISp[i].sex=p[j].sex;//PARTp[j].sex=num;// HERE

for my three arrays in a struct, thought there might be a more logical way when they are in a struct.

 

EDIT:

now it looks like this:

    int sk = p[i].lytis;    p[i].lytis=p[j].lytis;     p[j].lytis=sk;    int sk1 = p[i].ranka;     p[i].ranka=p[j].ranka;     p[j].ranka=sk1;   int sk2 = p[i].dydis;   p[i].dydis=p[j].dydis;    p[j].dydis=sk2;

i5-4690k, R9 380 4gb, 8gb-1600MHz ram, corsair vs 550w, astrock h97m anniversary.

 

Link to comment
https://linustechtips.com/topic/468707-sort-arrays-c/#findComment-6286815
Share on other sites

Link to post
Share on other sites

Example using std::vector :

#include <iostream>#include <vector>#include <algorithm>using namespace std;struct glove{    int sex;//  3 = male, 4 - female    int hand;// 1 - left , 2 - right    int size;    glove(int s, int h , int sz)    {        sex = s;        hand = h;        size = sz;    }    void print()    {        cout << sex << ' ' << hand << ' ' << size << '\n';    }};struct comp_sex{    inline bool operator() (const glove& glove1, const glove& glove2)    {        return (glove1.sex < glove2.sex);    }};int main(){    vector<glove> v;    v.push_back(glove(3,1 , 42));    v.push_back(glove(4, 2 , 43));    v.push_back(glove(3, 1 , 27));    sort(v.begin(),v.end() , comp_sex() );    for(int i = 0; i < v.size() ; i++)    v[i].print();    return 0;}

i5 4670k @ 4.2GHz (Coolermaster Hyper 212 Evo); ASrock Z87 EXTREME4; 8GB Kingston HyperX Beast DDR3 RAM @ 2133MHz; Asus DirectCU GTX 560; Super Flower Golden King 550 Platinum PSU;1TB Seagate Barracuda;Corsair 200r case. 

Link to comment
https://linustechtips.com/topic/468707-sort-arrays-c/#findComment-6286816
Share on other sites

Link to post
Share on other sites

 

Example using vector :

#include <iostream>#include <vector>#include <algorithm>struct glove{    int sex;//  3 = male, 4 - female    int hand;// 1 - left , 2 - right    int size;    glove(int s, int h , int sz){ sex = s; hand = h; size = sz;}};struct comp_sex(){    inline bool operator() (const glove& glove1, const glove& glove2)    {        return (glove1.sex < glove2.sex);    }};int main(){    vector<glove> v;    v.push_back(glove(3,1 , 42));    v.push_back(glove(4, 2 , 43));    v.push_back(glove(3, 1 , 27));    sort(v.begin(),v.end() , comp_sex() );    return 0;}

i'm doing the exam exercises and i must use arrays. They dont teach us vectors.

i5-4690k, R9 380 4gb, 8gb-1600MHz ram, corsair vs 550w, astrock h97m anniversary.

 

Link to comment
https://linustechtips.com/topic/468707-sort-arrays-c/#findComment-6286837
Share on other sites

Link to post
Share on other sites

i'm doing the exam exercises and i must use arrays. They dont teach us vectors.

As long as they're real arrays and not pointers, and you're using c++14, std::sort works on arrays too.

int arr[100] = blah blah blah;std::sort(std::begin(arr), std::end(arr), some_compare_function/struct/lambda);

Also std has a swap function that takes 2 of anything and swaps all their values. http://en.cppreference.com/w/cpp/algorithm/swap

 

Edit: unrelated but your glove constructor should really use an initializer list

struct glove{    int sex;//  3 = male, 4 - female    int hand;// 1 - left , 2 - right    int size;    glove(int s, int h , int sz)     : sex(s), hand(h), size(sz)     {}};

1474412270.2748842

Link to comment
https://linustechtips.com/topic/468707-sort-arrays-c/#findComment-6287886
Share on other sites

Link to post
Share on other sites

 

As long as they're real arrays and not pointers, and you're using c++14, std::sort works on arrays too.

int arr[100] = blah blah blah;std::sort(std::begin(arr), std::end(arr), some_compare_function/struct/lambda);

Also std has a swap function that takes 2 of anything and swaps all their values. http://en.cppreference.com/w/cpp/algorithm/swap

 

Edit: unrelated but your glove constructor should really use an initializer list

struct glove{    int sex;//  3 = male, 4 - female    int hand;// 1 - left , 2 - right    int size;    glove(int s, int h , int sz)     : sex(s), hand(h), size(sz)     {}};

So sort(begin(arr), end(arr), arr>arr[j]) like this?

i5-4690k, R9 380 4gb, 8gb-1600MHz ram, corsair vs 550w, astrock h97m anniversary.

 

Link to comment
https://linustechtips.com/topic/468707-sort-arrays-c/#findComment-6293394
Share on other sites

Link to post
Share on other sites

So sort(begin(arr), end(arr), arr>arr[j]) like this?

arr>arr[j] is just a bool. You need a function that can be called over and over that compares the sex of each glove. 

There are several ways to do it. You could create a callable struct like in Nineshadows example, overload operator< inside glove in which case you wont need the third parameter in the sort function or use a lambda. 

 

My preferred way is a lambda but if you haven't even learned vectors yet you probably shouldn't use something that advanced. But anyway it would look like this

std::sort(std::begin(gs), std::end(gs), [](const auto& g1, const auto& g2) noexcept { return g1.sex < g2.sex; });

1474412270.2748842

Link to comment
https://linustechtips.com/topic/468707-sort-arrays-c/#findComment-6295160
Share on other sites

Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

×