根據自己理解的oracle sequence的方式,實現了下,並做了性能測試,
測試環境爲公司報廢的筆記本電腦 dell E4300 ubuntu 13 64位系統.
代碼實現:
#include <stdio.h>
#include <stdlib.h>
#include <pthread.h>
#include <sys/time.h>
/**
* created by gongbo.yxh
seq mod
2013-06-11
**/
#define SEQ_CACHE_SIZE 1000
#define START 1
//兩個seq cache
unsigned long long * seq_buf;
unsigned long long int *seq_pointer;
int isprepared = 1; //是否準備好
unsigned long long int seq_extend_next_val = SEQ_CACHE_SIZE + 1;
int is_consumer_head = 1; //在定長數組中,是否生產者的指針在前面
unsigned long long int *seq_producer; //生產者指針
unsigned long long int *seq_consumer; //消費者
/**
初始話,將兩個數組構造好,並按照sequence的要求來構造
程序關閉的時候:記住要銷燬內存哦:
不銷燬也不存在內存泄漏的:
**/
void init()
{
seq_buf = (unsigned long long int *)calloc((size_t)SEQ_CACHE_SIZE,(size_t)sizeof(unsigned long long int));
if(seq_buf == NULL){
printf("ERROR:no memory!\n");
exit(1);
}
for(int i=0;i < SEQ_CACHE_SIZE;i++)
{
seq_buf[i] = START + i;
}
seq_pointer = seq_buf;
seq_consumer = seq_buf;
seq_producer = seq_buf;
}
/**
* 輸出打印,cache中的值:
**/
void disp()
{
printf("first_a value:\n");
for(int i=0;i < SEQ_CACHE_SIZE-1;i++)
{
printf("%lld\t",seq_buf[i]);
}
printf("\n");
}
//串行化的getseq,獲取序列值
unsigned long long int getseq_v1()
{
if(seq_pointer - seq_buf == SEQ_CACHE_SIZE - 1 )
{
unsigned long long int rtn_val = *seq_pointer;
//更新 buf
for(int i=0;i <= SEQ_CACHE_SIZE-1;i++)
{
seq_buf[i] = seq_extend_next_val + i;
}
//next val 要增加
seq_extend_next_val = seq_extend_next_val + SEQ_CACHE_SIZE;
seq_pointer = seq_buf;
return rtn_val;
}else{
unsigned long long int *p_rtn = seq_pointer;
seq_pointer++;
return *p_rtn;
}
}
// ----------------- test ---------------
struct timeval dwStart;
struct timeval dwEnd;
unsigned long dwTime=0;
//測試v1的getseq函數
void test_v1()
{
gettimeofday(&dwStart,NULL); //記錄開始時間: 用於性能測量
unsigned long long int num;
for(int i = 0;i < 10;i++)
{
num = getseq_v1();
//printf("%lld\t",num);
}
gettimeofday(&dwEnd,NULL); //記錄結束時間: 用於性能測量
dwTime = 1000000*(dwEnd.tv_sec-dwStart.tv_sec)+(dwEnd.tv_usec-dwStart.tv_usec);
printf("%ld\n",dwTime);
}
int main(void)
{
init();
//disp();
test_v1();
return 0;
}