[lnkForumImage]
TotalShareware - Download Free Software

Confronta i prezzi di migliaia di prodotti.
Asp Forum
 Home | Login | Register | Search 


 

Forums >

comp.lang.c

bubble sort in structure

cerr

3/18/2011 5:05:00 PM

Hi There,

I have no problem doing a bubble sort in an array but what if i need
to keep an identifier that is linked to the value so i always know
which values is where?
I have a little array with three "offset" elements and i would like to
sort them so that the smallest offset is at position 0. I can do that
with an array, n.p.:
// Bubble sort offset times
for (ctr=0;ctr<OFFSET_ARR_SZ;ctr++) {
if (iarray[ctr] > iarray[ctr+1]) {
//Here a swap is needed
temp=iarray[ctr+1];
iarray[ctr+1]=iarray[ctr];
iarray[ctr]=temp;
}
}
but once they're sorted and i want to take action i need to know what
action to take after the first offset i.e. i need to keep some kind of
identifier. I am aware that I could just sort after applying some kind
of binary mask to keep an id in my value... but i imagine there's a
more transparent way e.g. by sorting values in a structure...?
Recommendations and hints appreciated!
Thanks!
7 Answers

Ben Bacarisse

3/18/2011 5:19:00 PM

0

cerr <ron.eggler@gmail.com> writes:

> I have no problem doing a bubble sort in an array but what if i need
> to keep an identifier that is linked to the value so i always know
> which values is where?
> I have a little array with three "offset" elements and i would like to
> sort them so that the smallest offset is at position 0. I can do that
> with an array, n.p.:
> // Bubble sort offset times
> for (ctr=0;ctr<OFFSET_ARR_SZ;ctr++) {
> if (iarray[ctr] > iarray[ctr+1]) {
> //Here a swap is needed
> temp=iarray[ctr+1];
> iarray[ctr+1]=iarray[ctr];
> iarray[ctr]=temp;
> }
> }
> but once they're sorted and i want to take action i need to know what
> action to take after the first offset i.e. i need to keep some kind of
> identifier. I am aware that I could just sort after applying some kind
> of binary mask to keep an id in my value... but i imagine there's a
> more transparent way e.g. by sorting values in a structure...?
> Recommendations and hints appreciated!

An example might help. I think I know what you want but it's certainly
possible I've misunderstood.

One answer might be sort "indirectly". Rather than sort the data, you
sort an array containing the indexes of the data items (you can use
pointers if you prefer). Start by setting A[i] = i and sort A by
comparing iarray[A[i]]. If that does not suit, you can use A to sort
iarray and to build another index, B, where B[i] contains the original
location of iarray[i].

--
Ben.

cerr

3/18/2011 5:26:00 PM

0

On Mar 18, 10:18 am, Ben Bacarisse <ben.use...@bsb.me.uk> wrote:
> cerr <ron.egg...@gmail.com> writes:
>
> An example might help.  I think I know what you want but it's certainly
> possible I've misunderstood.
>
> One answer might be sort "indirectly".  Rather than sort the data, you
> sort an array containing the indexes of the data items (you can use
> pointers if you prefer).  Start by setting A[i] = i and sort A by
> comparing iarray[A[i]].  If that does not suit, you can use A to sort
> iarray and to build another index, B, where B[i] contains the original
> location of iarray[i].

Hi Ben,

Thanks for getting back - not sure if I understood. I just implemented
a sort the alternative way i described above. That may help you to
understand:

iarray[0]=0; //SYNC
iarray[1]=500; //LPR
iarray[2]=200; //OVR

iarray[0]|=0x10000000; // set SYNC ID bit
iarray[1]|=0x20000000; // set LPR ID bit
iarray[2]|=0x40000000; // set OVR ID bit

// Bubble sort offset times
for (ctr=0;ctr<OFFSET_ARR_SZ;ctr++) {
if ((iarray[ctr]&0x00FFFFFF) > (iarray[ctr+1]&0x00FFFFFF)) {
//Here a swap is needed
temp=iarray[ctr+1];
iarray[ctr+1]=iarray[ctr];
iarray[ctr]=temp;
}
}

Then to "read" the sorted array I'd do it like this:
if (iarray[0]&&0xf0000000==0x10000000){
delay_us((iarray[0]&0x00FFFFFF))
SETSYNCTMR(timval);
} else if (iarray[0]&&0xf0000000==0x20000000){
delay_us((iarray[0]&0x00FFFFFF))
SETLPRTMR(timval);
} else if (iarray[0]&&0xf0000000==0x40000000){
delay_us((iarray[0]&0x00FFFFFF))
SETOVRTMR(timval);
}
and repeatr this for [1]&[2]

Scott Fluhrer

3/18/2011 7:20:00 PM

0


"cerr" <ron.eggler@gmail.com> wrote in message
news:b26e1dcf-a6b0-4d47-9875-b9deee265b4b@22g2000prx.googlegroups.com...
> Hi There,
>
> I have no problem doing a bubble sort in an array but what if i need
> to keep an identifier that is linked to the value so i always know
> which values is where?
> I have a little array with three "offset" elements and i would like to
> sort them so that the smallest offset is at position 0. I can do that
> with an array, n.p.:
> // Bubble sort offset times
> for (ctr=0;ctr<OFFSET_ARR_SZ;ctr++) {
> if (iarray[ctr] > iarray[ctr+1]) {
> //Here a swap is needed
> temp=iarray[ctr+1];
> iarray[ctr+1]=iarray[ctr];
> iarray[ctr]=temp;
> }
> }

Two nits (which really don't address your original question):

- The above code is not guarranteed to sort the array. Bubble sort, in
general, needs N-1 passes over the array to fully sort; what your code will
do is make sure that the largest element ends up in the last position, but
not much beyond that. For example, if the smallest element starts in
iarray[2], it'll get moved to iarray[1] (and not iarray[0] where it should
be).

- Is OFFSET_ARR_SZ one less than the size of the array? The last iteration
of the loop will reference iarray[OFFSET_ARR_SZ], and if OFFSET_ARRAY_SZ is
(say) the size of the array, that's past the end.

--
poncho


Ben Bacarisse

3/18/2011 9:11:00 PM

0

cerr <ron.eggler@gmail.com> writes:

> On Mar 18, 10:18 am, Ben Bacarisse <ben.use...@bsb.me.uk> wrote:
>> cerr <ron.egg...@gmail.com> writes:
>>
>> An example might help.  I think I know what you want but it's certainly
>> possible I've misunderstood.
>>
>> One answer might be sort "indirectly".  Rather than sort the data, you
>> sort an array containing the indexes of the data items (you can use
>> pointers if you prefer).  Start by setting A[i] = i and sort A by
>> comparing iarray[A[i]].  If that does not suit, you can use A to sort
>> iarray and to build another index, B, where B[i] contains the original
>> location of iarray[i].
<snip>

> Thanks for getting back - not sure if I understood. I just implemented
> a sort the alternative way i described above. That may help you to
> understand:
>
> iarray[0]=0; //SYNC
> iarray[1]=500; //LPR
> iarray[2]=200; //OVR
>
> iarray[0]|=0x10000000; // set SYNC ID bit
> iarray[1]|=0x20000000; // set LPR ID bit
> iarray[2]|=0x40000000; // set OVR ID bit
>
> // Bubble sort offset times
> for (ctr=0;ctr<OFFSET_ARR_SZ;ctr++) {
> if ((iarray[ctr]&0x00FFFFFF) > (iarray[ctr+1]&0x00FFFFFF)) {
> //Here a swap is needed
> temp=iarray[ctr+1];
> iarray[ctr+1]=iarray[ctr];
> iarray[ctr]=temp;
> }
> }

This is not a bubble sort. It's not even well-defined unless
OFFSET_ARR_SZ is not what it claims to be!

> Then to "read" the sorted array I'd do it like this:
> if (iarray[0]&&0xf0000000==0x10000000){
> delay_us((iarray[0]&0x00FFFFFF))
> SETSYNCTMR(timval);
> } else if (iarray[0]&&0xf0000000==0x20000000){
> delay_us((iarray[0]&0x00FFFFFF))
> SETLPRTMR(timval);
> } else if (iarray[0]&&0xf0000000==0x40000000){
> delay_us((iarray[0]&0x00FFFFFF))
> SETOVRTMR(timval);
> }
> and repeatr this for [1]&[2]

It's not 100% clear. A guess: the fact the IDs are single bits is not
significant -- you won't ever combine them into a mask?

I suspect that a struct might be what you need. You can keep the data
(is it a time?) and the ID together. Another, similar, approach is to
sort two arrays in parallel: you have another array that contains the
IDs and you swap its elements whenever you swap a iarray pair.

--
Ben.

Keith Thompson

3/18/2011 9:31:00 PM

0

cerr <ron.eggler@gmail.com> writes:
> I have no problem doing a bubble sort in an array but what if i need
> to keep an identifier that is linked to the value so i always know
> which values is where?
[...]

I hope you're aware that bubble sort is useful primarily as a coding
exercise. There are much better sorting algorithms (in fact, there
aren't many worse ones) and the standard qsort() will implement
one of them.

(Bubble sort might be useful in some cases where the list is already
almost sorted, but even there there might be better choices.)

--
Keith Thompson (The_Other_Keith) kst-u@mib.org <http://www.ghoti.ne...
Nokia
"We must do something. This is something. Therefore, we must do this."
-- Antony Jay and Jonathan Lynn, "Yes Minister"

pete

3/19/2011 3:29:00 AM

0

cerr wrote:
>
> Hi There,
>
> I have no problem doing a bubble sort in an array but what if i need
> to keep an identifier that is linked to the value so i always know
> which values is where?
> I have a little array with three "offset" elements and i would like to
> sort them so that the smallest offset is at position 0. I can do that
> with an array, n.p.:
> // Bubble sort offset times
> for (ctr=0;ctr<OFFSET_ARR_SZ;ctr++) {
> if (iarray[ctr] > iarray[ctr+1]) {
> //Here a swap is needed
> temp=iarray[ctr+1];
> iarray[ctr+1]=iarray[ctr];
> iarray[ctr]=temp;
> }
> }
> but once they're sorted and i want to take action i need to know what
> action to take after the first offset i.e. i need to keep some kind of
> identifier. I am aware that I could just sort after applying some kind
> of binary mask to keep an id in my value... but i imagine there's a
> more transparent way e.g. by sorting values in a structure...?
> Recommendations and hints appreciated!
> Thanks!

/* BEGIN new.c output */

Before sorting by data:
array[0] data is 0, type is SYNC
array[1] data is 500, type is LPR
array[2] data is 200, type is OVR

After sorting by data:
array[0] data is 0, type is SYNC
array[1] data is 200, type is OVR
array[2] data is 500, type is LPR

/* END new.c output */



/* BEGIN new.c */

#include <stdio.h>

#define E_TYPE struct i e_type
#define MOV(A, B) ((void)(*(A) = *(B)))
#define GT(A, B) ((A) -> data > (B) -> data)

#define NMEMB(A) (sizeof (A) / sizeof *(A))

typedef E_TYPE;

struct i {
unsigned data;
char *type;
};

void sisort(e_type *array, size_t nmemb);

int
main(void)
{
unsigned index;
struct i array[] = {
{ 0, "SYNC"},
{500, "LPR" },
{200, "OVR" }
};

puts("/* BEGIN new.c output */\n");
puts("Before sorting by data:");
for (index = 0; index != NMEMB(array); ++index) {
printf("array[%u] data is %3u, type is %s\n",
index, array[index].data, array[index].type);
}
sisort(array, NMEMB(array));
puts("\nAfter sorting by data:");
for (index = 0; index != NMEMB(array); ++index) {
printf("array[%u] data is %3u, type is %s\n",
index, array[index].data, array[index].type);
}
puts("\n/* END new.c output */");
return 0;
}

void
sisort(e_type *array, size_t nmemb)
{
e_type *base, *low, *high, temp;

if (nmemb-- > 1) {
base = array;
do {
low = array++;
if (GT(low, array)) {
high = array;
MOV(&temp, high);
do {
MOV(high, low);
if (--high == base) {
break;
}
--low;
} while (GT(low, &temp));
MOV(high, &temp);
}
} while (--nmemb != 0);
}
}

/* END new.c */


--
pete

Malcolm McLean

3/19/2011 10:51:00 AM

0

On Mar 18, 11:31 pm, Keith Thompson <ks...@mib.org> wrote:
> cerr <ron.egg...@gmail.com> writes:
>
> (Bubble sort might be useful in some cases where the list is already
> almost sorted, but even there there might be better choices.)
>
These situations crop up quite a bit for real.

For instance imagine a virtual camera moving through a 3d world of
polygons. To draw the polygones correctly, you need to sort by z
order. However the camera will only move a small amount each frame.
Some of the ploygons might also move, if it's a dynamic world, but
again not by much.