读书人

算法搞不定一晚上没睡着!大清早起来

发布时间: 2012-02-29 16:44:10 作者: rapoo

算法搞不定,一晚上没睡着!大清早起来请教高手
有三个线程,线程A负责采集数据,线程B负责处理数据,线程C负责发送数据。
我现在在内存中分配了一大块Pool内存,用于存放和处理数据的缓存。该缓存为固定长度的数据数组,最多可放置256个采集到的数据内容。
我原来采用先进先出的静态环形队列,A采集到数据后,将数据内容放到Pool中,并设置标记表明该位置有数据且数据已经准备好。B从Pool中取已经准备好的数据进行处理,处理完毕后设置标记表明该位置的数据已经处理完毕。而C从Pool中取已经处理完毕的数据,发送数据后再设置该位置没有数据可以重新利用。

PData AllocData(PPOOL Pool) //从缓冲池中分配一个数据
{
ULONG CurrentPosition;
PData pData;

CurrentPosition = Pool-> AllocIndex % Pool-> Depth;
pData = &(Pool-> PoolStartAddress[CurrentPosition]);

if(pData-> Flag == FLAG_NO_Data)
{
Pool-> AllocIndex ++;
pData-> Flag = FLAG_HAS_Data;

return pData;
}

else
return NULL;
}

PData CheckReadyData(PPOOL Pool) //从缓冲池中取一个准备好的数据
{
ULONG CurrentPosition;
PData pData;

CurrentPosition = Pool-> ReadyIndex % Pool-> Depth;
pData = &(Pool-> PoolStartAddress[CurrentPosition]);

if((pData-> Flag & FLAG_HAS_Data) && (pData-> Flag & FLAG_Data_READY) && !(pData-> Flag & FLAG_Data_DONE))
{
Pool-> ReadyIndex ++;

return pData;
}

else
{
return NULL;
}
}

PData CheckDoneData(PPOOL Pool) //从缓冲池中取一个处理完毕的数据
{
ULONG CurrentPosition;
PData pData;

CurrentPosition = Pool-> DoneIndex % Pool-> Depth;
pData = &(Pool-> PoolStartAddress[CurrentPosition]);

if((pData-> Flag & FLAG_HAS_Data) && (pData-> Flag & FLAG_Data_DONE))
{
Pool-> DoneIndex ++;

return pData;
}

else
{
return NULL;
}
}

VOID FreeData(PData pData) //释放数据
{
pData-> Flag = FLAG_NO_Data;
}

VOID SetDataReady(PData pData) //数据包内容已经准备好
{
pData-> Flag |= FLAG_Data_READY;
}

VOID SetDataDone(PData pData) //数据包内容已经准备好
{
pData-> Flag |= FLAG_Data_DONE;
}

A:
pData = AllocData(Pool);
if(pData)
{
......
SetDataReady(pData);
}

B:
while(pData = CheckReadyData(Pool))
{
......
SetDataDone(pData);
}

C:
while(pData = CheckDoneData(Pool))
{
......
FreeData(pData);
}

可是C采用多线程发送数据,发送数据有快有慢,释放数据的先后也有先有后,导致三者没法同步。请问高手有什么好的算法?




[解决办法]
应该设置临界区,在处理pool时不让其他线程重入
[解决办法]
struct data_block {
data_block *next;
int buf[256];
};
class C_memory {
public:
C_memory(int count);
~C_memory();
public:
data_block *alloc();
void free(data_block *);
};
class C_pool {
C_lock m_lock;
data_block *m_data_list;
public:
void push(data_block *);
data_block *pop();
};
class C_worker {
C_memory m_allocer;
C_pool m_req_pool;
C_pool m_ready_pool;


static void thread_proc1(C_worker *This);
static void thread_proc2(C_worker *This);
static void thread_proc3(C_worker *This);
int m_use_count;
bool m_running;
public:
bool start();
void stop();
};
void C_worker::thread_proc1(C_worker *This)
{
this-> m_use_count++;
while (This-> m_running) {
data_block *buf = This-> m_allocer.alloc();
if ( ! data_block ) Sleep(1);
else {
//读
      ...
This-> m_req_pool.push(data_block);
}
}
this-> m_use_count--;
}
void C_worker::thread_proc2(C_worker *This)
{
this-> m_use_count++;
while (This-> m_running) {
data_block *buf = This-> m_req_pool.pop();
if ( ! data_block ) Sleep(1);
else {
//处理
      ...
This-> m_ready_pool.push(data_block);
}
}
this-> m_use_count--;

}
void C_worker::thread_proc3(C_worker *This)
{
this-> m_use_count++;

while (This-> m_running) {
data_block *buf = This-> m_ready_pool.pop();
if ( ! data_block ) Sleep(1);
else {
//发送
      ...
This-> m_allocer.free(data_block);
}
}
this-> m_use_count--;

}

int main()
{
C_worker worker;
worker.start();
getchar();
worker.stop();
return 0;
}

读书人网 >软件架构设计

热点推荐