0

単純に株価の配列を保持する循環バッファー プログラムを完成させようとしています。ただし、循環バッファーを縮小すると、出力が正しくないように見えます。

バッファを縮小する条件は、バッファ内のスペースの 3/4 が空いている場合、バッファを 1/2 縮小することです。縮小/拡大するための私のコードは次のとおりです。

void cbuf_update(cbuf *cb_ptr, unsigned int time, double rate){
    int threeFourths;
    threeFourths = (cb_ptr->maxSize/4)*3;

    if((cb_ptr->maxSize != startSize) && cb_ptr->freeSlots >= threeFourths){
        printf("Shrinking!\n");
        int newSize;
        newSize = (cb_ptr->maxSize/2)-1;
        cbuf *newBuffer = malloc(sizeof(cbuf) + newSize * sizeof(quote));
        newBuffer ->maxSize = (cb_ptr->maxSize/2);
        newBuffer ->freeSlots = newBuffer->maxSize - (cb_ptr->maxSize - cb_ptr->freeSlots);
        int x;
        int counter;
        int y;
        counter = 0;
        if(cb_ptr->end > cb_ptr->start){
            for(x = cb_ptr->end; x < cb_ptr->maxSize; x ++){
                if(cb_ptr->quoteBuffer[x].time != -1){
                    newBuffer->quoteBuffer[counter].time = cb_ptr->quoteBuffer[x].time;
                    newBuffer->quoteBuffer[counter].rate = cb_ptr->quoteBuffer[x].rate;
                    counter ++;
                }
            }   
            for(y = 0; y < cb_ptr->start; y++){
                if(cb_ptr->quoteBuffer[y].time != -1){
                    newBuffer->quoteBuffer[counter].time = cb_ptr->quoteBuffer[y].time;
                    newBuffer->quoteBuffer[counter].rate = cb_ptr->quoteBuffer[y].rate;
                    counter++;
                }
            }
        }
        if(cb_ptr->end < cb_ptr->start){
            //printf("second condition\n");
            for(x = cb_ptr->end; x < cb_ptr->start; x ++){
                if(cb_ptr->quoteBuffer[x].time != -1){

                    newBuffer->quoteBuffer[counter].time = cb_ptr->quoteBuffer[x].time;
                    newBuffer->quoteBuffer[counter].rate = cb_ptr->quoteBuffer[x].rate;
                    counter ++;
                }
            }       
        }
        newBuffer->start = counter;
        newBuffer->end = 0;
        cbuf_dump(newBuffer);
        *cb_ptr = *newBuffer;       

    }


    if(cb_ptr->freeSlots == 0){
        printf("EXPANDING CIRCULAR BUFFER!\n");
        int newSize;
        newSize = (cb_ptr->maxSize * 2) - 1;
        cbuf *newBuffer = malloc(sizeof(cbuf) + newSize * sizeof(quote));
        newBuffer->maxSize = cb_ptr->maxSize * 2;
        newBuffer->start = cb_ptr->start;
        newBuffer->end = cb_ptr->end;
        newBuffer->freeSlots = newBuffer->maxSize - cb_ptr->maxSize;
        int x;
        int counter;
        counter = 0;
        for(x = cb_ptr->end; x < cb_ptr->maxSize; x ++){
            newBuffer->quoteBuffer[counter].time = cb_ptr->quoteBuffer[x].time;
            newBuffer->quoteBuffer[counter].rate = cb_ptr->quoteBuffer[x].rate;
            counter ++;
        }
        int y;
        for(y = 0; y < cb_ptr->start; y ++){
            newBuffer->quoteBuffer[counter].time = cb_ptr->quoteBuffer[y].time;
            newBuffer->quoteBuffer[counter].rate = cb_ptr->quoteBuffer[y].rate;
            counter++;
        }
        newBuffer->start = cb_ptr->maxSize;
        newBuffer->end = 0;

        *cb_ptr = *newBuffer;



    }   


    //If the start pointer has reached the end of the array and there are still free slots back at the beginning of the array, loop back.   
    if(cb_ptr->start == cb_ptr->maxSize && cb_ptr->freeSlots > 0){
        //printf("Cannot insert time: %d\n", time);
        cb_ptr->start = 0;
    };
    cb_ptr->quoteBuffer[cb_ptr->start].time = time;
    cb_ptr->quoteBuffer[cb_ptr->start].rate = rate;
    cb_ptr->start = cb_ptr->start +1;
    cb_ptr->freeSlots = cb_ptr->freeSlots -1;

    //If any quote in the array is older than 5 minutes when compared to the current quote, flag it as null and move the end pointer up one.
    //Also, clear up a freeSlot.
    int x;
    for(x = cb_ptr->end; x < (cb_ptr->start); x ++){

        if((time) - (cb_ptr->quoteBuffer[x].time) >= fiveMin){
            cb_ptr->end = cb_ptr->end + 1;
            cb_ptr->quoteBuffer[x].time = -1;
            cb_ptr->quoteBuffer[x].rate = -1.00;
            cb_ptr->freeSlots = cb_ptr->freeSlots +1;
        }
    }


}

バッファーをダンプ (出力) するためのコードは次のとおりです。

void cbuf_dump(cbuf *cb_ptr){
    printf("*****\t DUMPING \t*****\n");

    if(cb_ptr->start > cb_ptr->end){
        //printf("first dump cond.\n");
        printf("start: %d\t end:%d\n", cb_ptr->start, cb_ptr->end);
        int x;
        for(x = cb_ptr->end; x<(cb_ptr->start); x++){
            printf("%d.) time = %d, \t rate = %f\n",x,(cb_ptr->quoteBuffer[x].time),(cb_ptr->quoteBuffer[x].rate));
        }
    }

    /*
    If the start pointer has been wrapped back around to the beginning of the circular buffer, then the end pointer must be at an index that is         greater than the start index. For this, we need to print out the data ranging from the end pointer to the end of the array, and then the        data from the start pointer to the end pointer provided the data isn't flagged as null (having -1 for both entries in the quote struct).
    */
    if(cb_ptr->end >= cb_ptr->start){
        //printf("Secondary condition\n");
        int x;
        for(x=cb_ptr->end; x < cb_ptr->maxSize; x ++){
            printf("%d.) time = %d, \t rate = %f\n",x,(cb_ptr->quoteBuffer[x].time),(cb_ptr->quoteBuffer[x].rate));
        }
        int y;
        for(y = 0; y < cb_ptr->start; y ++){
            if(cb_ptr->quoteBuffer[y].time != -1){
                printf("%d.) time = %d, \t rate = %f\n",y,(cb_ptr->quoteBuffer[y].time),(cb_ptr->quoteBuffer[y].rate));
            }
        }
    }

    //printf("freeslots = %d\n", cb_ptr->freeSlots);
}

最後に、私のメインは次のとおりです。

int main(){

    cbuf *cb1 ;

    cb1 = cbuf_init() ;
    cbuf_update(cb1, 60, 1.291) ;
    cbuf_update(cb1, 63, 1.287) ;
    cbuf_update(cb1, 63, 1.231) ;
    cbuf_update(cb1, 69, 1.229) ;
    cbuf_update(cb1, 72, 1.247) ;
    cbuf_update(cb1,361,1.291);
    cbuf_update(cb1, 411, 1.291) ;
    cbuf_update(cb1, 412, 1.281) ;
    cbuf_update(cb1, 413, 1.292) ;
    cbuf_update(cb1, 414, 1.284) ;
    cbuf_update(cb1, 414, 1.290) ;
    cbuf_update(cb1, 511, 1.241) ;
    cbuf_update(cb1, 512, 1.251) ;
    cbuf_update(cb1, 513, 1.232) ;
    cbuf_update(cb1, 514, 1.202) ;
    cbuf_update(cb1, 517, 1.119) ;
    cbuf_update(cb1, 551, 1.080) ;
    cbuf_update(cb1, 552, 1.081) ;
    cbuf_update(cb1, 553, 1.079) ;
    cbuf_update(cb1, 554, 1.088) ;
    cbuf_update(cb1, 561, 1.072) ;
    cbuf_update(cb1, 562, 1.113) ;
    cbuf_update(cb1, 563, 1.091) ;
    cbuf_update(cb1, 564, 1.092) ;
    cbuf_update(cb1, 571, 1.089) ;
    cbuf_update(cb1, 572, 1.073) ;
    cbuf_update(cb1, 573, 1.061) ;
    cbuf_update(cb1, 574, 1.111) ;
    cbuf_update(cb1, 581, 1.119) ;
    cbuf_update(cb1, 582, 1.123) ;
    cbuf_update(cb1, 583, 1.151) ;
    cbuf_update(cb1, 584, 1.153) ;  
    cbuf_dump(cb1);
    cbuf_update(cb1, 750, 1.200) ;
    cbuf_dump(cb1) ;
    cbuf_update(cb1, 818, 1.210) ;
    cbuf_dump(cb1) ;
    cbuf_update(cb1, 868, 1.230) ;
    cbuf_dump(cb1) ;
    cbuf_update(cb1, 878, 1.230) ;
    cbuf_dump(cb1) ;
    cbuf_update(cb1, 900, 1.240) ;
    cbuf_dump(cb1) ;
    cbuf_update(cb1, 2000, 1.240) ;
    cbuf_dump(cb1) ;
    return 0;

}

最後の出力は次のようになります。

*** Circular Buffer Dump ***
size = 11, max = 40
start = 19, end = 29

19: time = 571,  rate = 1.089000
20: time = 572,  rate = 1.073000
21: time = 573,  rate = 1.061000
22: time = 574,  rate = 1.111000
23: time = 581,  rate = 1.119000
24: time = 582,  rate = 1.123000
25: time = 583,  rate = 1.151000
26: time = 584,  rate = 1.153000
27: time = 750,  rate = 1.200000
28: time = 818,  rate = 1.210000
29: time = 868,  rate = 1.230000
****************************

Shrinking circular buffer: old max = 40, new max = 20


*** Circular Buffer Dump ***
size = 8, max = 20
start = 3, end = 10

3: time = 581,  rate = 1.119000
4: time = 582,  rate = 1.123000
5: time = 583,  rate = 1.151000
6: time = 584,  rate = 1.153000
7: time = 750,  rate = 1.200000
8: time = 818,  rate = 1.210000
9: time = 868,  rate = 1.230000
10: time = 878,  rate = 1.230000
****************************

Shrinking circular buffer: old max = 20, new max = 10


*** Circular Buffer Dump ***
size = 5, max = 10
start = 1, end = 5

1: time = 750,  rate = 1.200000
2: time = 818,  rate = 1.210000
3: time = 868,  rate = 1.230000
4: time = 878,  rate = 1.230000
5: time = 900,  rate = 1.240000
****************************



*** Circular Buffer Dump ***
size = 1, max = 10
start = 6, end = 6

6: time = 2000,  rate = 1.240000
****************************

ただし、私の出力は次のように終了し続けます。

*****    DUMPING    *****
start: 30    end:19
19.) time = 571,     rate = 1.089000
20.) time = 572,     rate = 1.073000
21.) time = 573,     rate = 1.061000
22.) time = 574,     rate = 1.111000
23.) time = 581,     rate = 1.119000
24.) time = 582,     rate = 1.123000
25.) time = 583,     rate = 1.151000
26.) time = 584,     rate = 1.153000
27.) time = 750,     rate = 1.200000
28.) time = 818,     rate = 1.210000
29.) time = 868,     rate = 1.230000
*****    DUMPING    *****
start: 31    end:23
23.) time = 581,     rate = 1.119000
24.) time = 582,     rate = 1.123000
25.) time = 583,     rate = 1.151000
26.) time = 584,     rate = 1.153000
27.) time = 750,     rate = 1.200000
28.) time = 818,     rate = 1.210000
29.) time = 868,     rate = 1.230000
30.) time = 878,     rate = 1.230000
Shrinking!
*****    DUMPING    *****
start: 9     end:8
8.) time = 900,      rate = 1.240000
Shrinking!
*****    DUMPING    *****
start: 2     end:1
1.) time = 2000,     rate = 1.240000

明らかにフォーマットは異なりますが、数字は一致するはずです。バッファに 900 の時間が追加されるとすぐに、タイム コード 581 ~ 878 がすべて 900 から 5 分以上離れていると思われる理由がよくわかりません (印刷の基準は、最新の引用符のみを印刷することです)。 5 分間のタイムスパンで)。581 ~ 600 は明らかに破棄されますが、残りはバッファに残っているはずです。

4

1 に答える 1

2

これを試して:

#include <stdio.h>
#include <stdlib.h>

enum { startSize = 0 };
enum { fiveMin = 5 * 60 };

typedef struct quote { int time; double rate; } quote;

typedef struct cbuf { int maxSize; int freeSlots; int start; int end; quote quoteBuffer[]; } cbuf;
static void cbuf_dump(cbuf *cb_ptr);

static void cbuf_update(cbuf **cb_dblptr, unsigned int time, double rate)
{
    cbuf *cb_ptr = *cb_dblptr;
    int threeFourths = (cb_ptr->maxSize/4)*3;

    if (cb_ptr->maxSize != startSize && cb_ptr->freeSlots >= threeFourths)
    {
        printf("Shrinking!\n");
        int newSize;
        newSize = (cb_ptr->maxSize/2)-1;
        cbuf *newBuffer = malloc(sizeof(cbuf) + newSize * sizeof(quote));
        newBuffer->maxSize = (cb_ptr->maxSize/2);
        newBuffer->freeSlots = newBuffer->maxSize - (cb_ptr->maxSize - cb_ptr->freeSlots);
        int counter = 0;
        if (cb_ptr->end > cb_ptr->start)
        {
            for (int x = cb_ptr->end; x < cb_ptr->maxSize; x++)
            {
                if (cb_ptr->quoteBuffer[x].time != -1)
                    newBuffer->quoteBuffer[counter++] = cb_ptr->quoteBuffer[x];
            }
            for (int y = 0; y < cb_ptr->start; y++)
            {
                if (cb_ptr->quoteBuffer[y].time != -1)
                    newBuffer->quoteBuffer[counter++] = cb_ptr->quoteBuffer[y];
            }
        }
        if (cb_ptr->end < cb_ptr->start)
        {

            for (int x = cb_ptr->end; x < cb_ptr->start; x++)
            {
                if (cb_ptr->quoteBuffer[x].time != -1)
                    newBuffer->quoteBuffer[counter++] = cb_ptr->quoteBuffer[x];
            }
        }
        newBuffer->start = counter;
        newBuffer->end = 0;
        cbuf_dump(newBuffer);
        *cb_dblptr = cb_ptr = newBuffer;
    }

    if (cb_ptr->freeSlots == 0)
    {
        printf("EXPANDING CIRCULAR BUFFER!\n");
        int newSize;
        newSize = (cb_ptr->maxSize * 2) - 1;
        cbuf *newBuffer = malloc(sizeof(cbuf) + newSize * sizeof(quote));
        newBuffer->maxSize = cb_ptr->maxSize * 2;
        newBuffer->start = cb_ptr->start;
        newBuffer->end = cb_ptr->end;
        newBuffer->freeSlots = newBuffer->maxSize - cb_ptr->maxSize;
        int counter = 0;
        for (int x = cb_ptr->end; x < cb_ptr->maxSize; x++)
            newBuffer->quoteBuffer[counter++] = cb_ptr->quoteBuffer[x];
        for (int y = 0; y < cb_ptr->start; y++)
            newBuffer->quoteBuffer[counter++] = cb_ptr->quoteBuffer[y];
        newBuffer->start = cb_ptr->maxSize;
        newBuffer->end = 0;
        *cb_dblptr = cb_ptr = newBuffer;
    }

    if (cb_ptr->start == cb_ptr->maxSize && cb_ptr->freeSlots > 0)
        cb_ptr->start = 0;
    cb_ptr->quoteBuffer[cb_ptr->start].time = time;
    cb_ptr->quoteBuffer[cb_ptr->start].rate = rate;
    cb_ptr->start = cb_ptr->start +1;
    cb_ptr->freeSlots = cb_ptr->freeSlots -1;

    for (int x = cb_ptr->end; x < (cb_ptr->start); x++)
    {
        if ((time) - (cb_ptr->quoteBuffer[x].time) >= fiveMin)
        {
            cb_ptr->end = cb_ptr->end + 1;
            cb_ptr->quoteBuffer[x].time = -1;
            cb_ptr->quoteBuffer[x].rate = -1.00;
            cb_ptr->freeSlots = cb_ptr->freeSlots +1;
        }
    }
}

static void cbuf_dump(cbuf *cb_ptr)
{
    printf("*****\t DUMPING \t*****\n");

    if (cb_ptr->start > cb_ptr->end)
    {
        printf("start: %d\t end:%d\n", cb_ptr->start, cb_ptr->end);
        for (int x = cb_ptr->end; x < cb_ptr->start; x++)
        {
            printf("%d.) time = %d, \t rate = %f\n",x,(cb_ptr->quoteBuffer[x].time),(cb_ptr->quoteBuffer[x].rate));
        }
    }

    if (cb_ptr->end >= cb_ptr->start)
    {
        for (int x = cb_ptr->end; x < cb_ptr->maxSize; x++)
        {
            printf("%d.) time = %d, \t rate = %f\n",x,(cb_ptr->quoteBuffer[x].time),(cb_ptr->quoteBuffer[x].rate));
        }
        for (int y = 0; y < cb_ptr->start; y++)
        {
            if (cb_ptr->quoteBuffer[y].time != -1)
            {
                printf("%d.) time = %d, \t rate = %f\n",y,(cb_ptr->quoteBuffer[y].time),(cb_ptr->quoteBuffer[y].rate));
            }
        }
    }
}

static cbuf *cbuf_init(void)
{
    return calloc(1, sizeof(cbuf));
}

int main(void)
{
    cbuf *cb1;

    cb1 = cbuf_init() ;
    cbuf_update(&cb1, 60, 1.291) ;
    cbuf_update(&cb1, 63, 1.287) ;
    cbuf_update(&cb1, 63, 1.231) ;
    cbuf_update(&cb1, 69, 1.229) ;
    cbuf_update(&cb1, 72, 1.247) ;
    cbuf_update(&cb1,361,1.291);
    cbuf_update(&cb1, 411, 1.291) ;
    cbuf_update(&cb1, 412, 1.281) ;
    cbuf_update(&cb1, 413, 1.292) ;
    cbuf_update(&cb1, 414, 1.284) ;
    cbuf_update(&cb1, 414, 1.290) ;
    cbuf_update(&cb1, 511, 1.241) ;
    cbuf_update(&cb1, 512, 1.251) ;
    cbuf_update(&cb1, 513, 1.232) ;
    cbuf_update(&cb1, 514, 1.202) ;
    cbuf_update(&cb1, 517, 1.119) ;
    cbuf_update(&cb1, 551, 1.080) ;
    cbuf_update(&cb1, 552, 1.081) ;
    cbuf_update(&cb1, 553, 1.079) ;
    cbuf_update(&cb1, 554, 1.088) ;
    cbuf_update(&cb1, 561, 1.072) ;
    cbuf_update(&cb1, 562, 1.113) ;
    cbuf_update(&cb1, 563, 1.091) ;
    cbuf_update(&cb1, 564, 1.092) ;
    cbuf_update(&cb1, 571, 1.089) ;
    cbuf_update(&cb1, 572, 1.073) ;
    cbuf_update(&cb1, 573, 1.061) ;
    cbuf_update(&cb1, 574, 1.111) ;
    cbuf_update(&cb1, 581, 1.119) ;
    cbuf_update(&cb1, 582, 1.123) ;
    cbuf_update(&cb1, 583, 1.151) ;
    cbuf_update(&cb1, 584, 1.153) ;
    cbuf_dump(cb1);
    cbuf_update(&cb1, 750, 1.200) ;
    cbuf_dump(cb1) ;
    cbuf_update(&cb1, 818, 1.210) ;
    cbuf_dump(cb1) ;
    cbuf_update(&cb1, 868, 1.230) ;
    cbuf_dump(cb1) ;
    cbuf_update(&cb1, 878, 1.230) ;
    cbuf_dump(cb1) ;
    cbuf_update(&cb1, 900, 1.240) ;
    cbuf_dump(cb1) ;
    cbuf_update(&cb1, 2000, 1.240) ;
    cbuf_dump(cb1) ;
    return 0;
}
于 2013-04-30T05:05:27.473 に答える