📄 queue.h
字号:
// Queue.h: interface for the CQueue class.
//
//////////////////////////////////////////////////////////////////////
#if !defined(AFX_QUEUE_H__2FE4BB4C_CF80_4DA4_8032_CF4D204BF298__INCLUDED_)
#define AFX_QUEUE_H__2FE4BB4C_CF80_4DA4_8032_CF4D204BF298__INCLUDED_
#if _MSC_VER > 1000
#pragma once
#endif // _MSC_VER > 1000
//调试代码
class CLllDlg;
/********************************************************************************************************************************\
int型队列封装类
支持多线程访问
\********************************************************************************************************************************/
class CQueue
{
struct SCS
{
CRITICAL_SECTION CS;
#ifdef _DEBUG
BOOL bEnter;//进入CS了吗?
#endif
SCS()
{
//初始化临界区对象
InitializeCriticalSection(&CS);
#ifdef _DEBUG
bEnter = FALSE;
#endif
}
//进入临界区
inline void Lock()
{
::EnterCriticalSection(&CS);
#ifdef _DEBUG
bEnter = TRUE;
#endif
}
//退出临界区
inline void UnLock()
{
::LeaveCriticalSection(&CS);
#ifdef _DEBUG
bEnter = FALSE;
#endif
}
}m_sCS; //整个SocketManager的临界区对象,在对m_pSocketRes整体进行操作(如果申请,释放socket时),并可能与其它线程发生冲突时使用
public:
BOOL Out(int *piData);
BOOL In(int iData);
inline CQueue(UINT nLength);
inline ~CQueue();
private:
inline BOOL IsEmpty();
inline BOOL IsFull();
UINT m_nTail; //队尾位置
UINT m_nHead; //队头位置
//-i-队头队尾指示变量(m_nHead、m_nTail)规则:
//-i-入队:m_nTail当前指示位置为空,入队后++
//-i-出队:m_nHead当前指示位置有效,出队后++
//-i-队空:m_nHead == m_nTail
//-i-队满:m_nTail++%后等于m_nHead
int* m_piQueue; //一个队列,(在内部,有一个不能用的位置)
UINT m_nQueueLength;//m_piQueue的元素个数
//调试代码
friend class CLllDlg;
};
//////////////////////////////////////////////////////////////////////
// Construction/Destruction
//////////////////////////////////////////////////////////////////////
/********************************************************************************************************************************\
唯一构造函数,传入队列 可 用 大小
\********************************************************************************************************************************/
inline CQueue::CQueue(UINT nLength)
{
ATLASSERT(nLength);
//申请队列内存
m_piQueue = new int[nLength + 1];//多出一个不能用,这是《数据结构》上推荐的做法
//记录m_piQueue所申请的元素个数
m_nQueueLength = nLength + 1;
//队头、尾复位。
m_nHead = m_nTail = 0;
//-i-队头队尾指示变量(m_nHead、m_nTail)规则:
//-i-入队:m_nTail当前指示位置为空,入队后++
//-i-出队:m_nHead当前指示位置有效,出队后++
//-i-队空:m_nHead == m_nTail
//-i-队满:m_nTail++%后等于m_nHead
}
inline CQueue::~CQueue()
{
//回收内存
delete []m_piQueue;
//m_piQueue元素个数清零
m_nQueueLength = 0;
//队头、尾复位。
m_nHead = m_nTail = 0;
}
/********************************************************************************************************************************\
队列是否已满
\********************************************************************************************************************************/
inline BOOL CQueue::IsFull()
{
//先进入临界区
m_sCS.Lock();
BOOL bRet;
if( ((m_nTail + 1) % m_nQueueLength) == m_nHead )
{
bRet = TRUE;//队满
}else
{
bRet = FALSE;//未满
}
//退出函数时退出临界区
m_sCS.UnLock();
return bRet;
}
/********************************************************************************************************************************\
队列是否为空
\********************************************************************************************************************************/
inline BOOL CQueue::IsEmpty()
{
//先进入临界区
m_sCS.Lock();
BOOL bRet = (m_nHead == m_nTail);//队头与队尾重合时为空
//退出函数时退出临界区
m_sCS.UnLock();
return bRet;
}
#endif // !defined(AFX_QUEUE_H__2FE4BB4C_CF80_4DA4_8032_CF4D204BF298__INCLUDED_)
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -