VC++自释放指针、自释放虚拟内存、自关闭句柄、局部作用域回调函数调用等辅助开发类

来源:互联网 发布:敲诈勒索软件 编辑:程序博客网 时间:2024/06/03 17:09

#pragma once#ifndef NULL#define NULL 0#endifnamespace RangeHelper{template <class T>class CAutoDeletePtr {//自动删除指针public:CAutoDeletePtr() : m_ptr(NULL) {}CAutoDeletePtr(T* ptr) {m_ptr = ptr;}~CAutoDeletePtr() {Free();}void Free() {if (!m_ptr) return;delete []m_ptr;m_ptr = NULL;}bool Allocate(size_t nElements) {Free();m_ptr = new T[nElements];if (!m_ptr) return false;return true;}void Attach(T* p) {ASSERT(p != NULL);m_ptr = p;}T* Detach() {T* p;p = m_p;m_p = NULL;return( p );}T operator[](int i) const{ASSERT((i>=0) && AfxIsValidAddress(m_ptr, sizeof(T)*i));return m_ptr[i];}T& operator[](int i){ASSERT((i>=0) && AfxIsValidAddress(m_ptr, sizeof(T)*i));return m_ptr[i];}CAutoDeletePtr<T>& operator=(const T* ptr){if ((m_ptr != NULL) && (m_ptr != ptr)){if (m_ptr != NULL){delete []m_ptr;m_ptr = NULL;}}m_ptr = const_cast<T*>(ptr);return *this;}operator T*() const {return m_ptr;}private:T *m_ptr;};template <class T>class CAutoReleaseVM//自释放虚拟内存{public:CAutoReleaseVM() :m_ptr(NULL), m_nCnt(0) {}CAutoReleaseVM(T* vmData, ULONG nCnt) {ASSERT(vmData);ASSERT(nCnt>0);m_ptr= vmData;m_nCnt= nCnt;}CAutoReleaseVM(ULONG nElementCnt, DWORD flAllocationType=MEM_COMMIT, DWORD flProtect=PAGE_READWRITE) : m_ptr(NULL) {AllocateVM(nElementCnt, flAllocationType, flProtect);}~CAutoReleaseVM(){FreeVM();}void FreeVM(){if (m_ptr) {VirtualFree(m_ptr, 0, MEM_RELEASE);m_nCnt= 0;m_ptr= NULL;}}BOOL AllocateVM(ULONG nElementCnt, DWORD flAllocationType=MEM_COMMIT, DWORD flProtect=PAGE_READWRITE){FreeVM();m_ptr= (T*)VirtualAlloc(NULL, nElementCnt*sizeof(T), flAllocationType, flProtect);m_nCnt= nElementCnt;return (m_ptr!=NULL);}BOOL ReAllocateVM(ULONG nElementCnt, BOOL bCopyOld=TRUE, DWORD flAllocationType=MEM_COMMIT, DWORD flProtect=PAGE_READWRITE){if (!bCopyOld)return AllocateVM(nElementCnt, flAllocationType, flProtect);T *tmp = (T*)VirtualAlloc(NULL, nElementCnt*sizeof(T), flAllocationType, flProtect);if (!tmp)return FALSE;memmove(tmp, m_ptr, min(nElementCnt, m_nCnt)*sizeof(T));m_ptr = tmp;m_nCnt= nElementCnt;return TRUE;}BOOL IsOK() {return (m_ptr!=NULL);}size_t GetDataBytes() {size_t nDataBytes = 0;if (IsOK()) {nDataBytes = GetTypeSize()*m_nCnt;}return nDataBytes;}size_t GetTypeSize() {return sizeof(T);}ULONG GetDataCount() {ULONG nDataCount = 0;if (IsOK()) {nDataCount = m_nCnt;}return nDataCount;}T operator[](size_t i) const{ASSERT((i>=0) && m_ptr && AfxIsValidAddress(m_ptr, sizeof(T)*i));return m_ptr[i];}T& operator[](size_t i){ASSERT((i>=0) && m_ptr && AfxIsValidAddress(m_ptr, sizeof(T)*i));return m_ptr[i];}operator T*() const {return m_ptr;}private:T*m_ptr;size_tm_nCnt;};class CAutoCloseHandle//自动关闭句柄类{public:CAutoCloseHandle(HANDLE* handle=NULL) : m_handle(handle){}CAutoCloseHandle& operator=(HANDLE* rh){if (m_handle) {CloseHandle(m_handle);m_handle = NULL;}m_handle = rh;return *this;}~CAutoCloseHandle(){CloseHandle(*m_handle);}private:HANDLE *m_handle;};template <class T>class CAutoDeleteArray : public CArray<T*, T*>{public:~CAutoDeleteArray() {RemoveAll();}void RemoveAt(INT_PTR nIndex, INT_PTR nCount = 1){ASSERT(nCount>0);for (INT_PTR i=nIndex; i!=min(nIndex+nCount, GetCount()); ++i){T *pItem = GetAt(i);delete pItem;}CArray::RemoveAt(nIndex, nCount);}void RemoveAll(){for (INT_PTR i=0; i!=GetCount(); ++i){T *pItem = GetAt(i);delete pItem;}CArray::RemoveAll();}};/*//CRangeFxnHelper使用示例class A{public:void func1(){cout << 1 << endl;}void func2(){cout << 2 << endl;}void test(){CRangeFxnHelper<A> a(this, &A::func1, &A::func2);}};*/template <class T>class CRangeFxnHelper//局部函数调用{typedef void(T::* MemFxnPtr)(void); //成员函数public:CRangeFxnHelper(T* pClassName,MemFxnPtr lpfxnEnter,MemFxnPtr lpfxnLeave = NULL) : m_pClassName(pClassName),m_lpfxnLeave(lpfxnLeave){ASSERT(pClassName != NULL);ASSERT(lpfxnEnter != NULL);(m_pClassName->*lpfxnEnter)();}~CRangeFxnHelper(){if (m_lpfxnLeave != NULL)(m_pClassName->*m_lpfxnLeave)();}private:T *m_pClassName;MemFxnPtr m_lpfxnLeave;};template <class T>class CAutoRevertBOOL//自动反置布尔变量{public:CAutoRevertBOOL(T *pObjBool, T initVal) : m_pObjBool(pObjBool),m_InitVal(initVal){ASSERT(pObjBool != NULL);*pObjBool = initVal;}~CAutoRevertBOOL(){*m_pObjBool = !m_InitVal;}private:T *m_pObjBool;T m_InitVal;};class CAutoDisableEnableChildCtls{public:CAutoDisableEnableChildCtls(HWND hwndParent, UINT nFirstExcludeChildCtrlID=-1, ...): m_hwndParent(hwndParent), m_bDisabled(FALSE){AddExcludeCtrlIDs(nFirstExcludeChildCtrlID);}~CAutoDisableEnableChildCtls(){if (m_bDisabled)SwitchStatus();}void SwitchStatus(){struct stEnumChild {BOOL*pChangeStatus;//改变状态CArray<UINT, UINT>*pArrayExcludeID;//无须进行状态改变的列表CArray<HWND, HWND>*pStatusChangedWND;//已经改变的窗口};class CEnumChildHelper{public:static BOOL __stdcall EnumChildProc(HWND hwnd, LPARAM lParam){stEnumChild *pParam= (stEnumChild *)lParam;LONG lStyle= GetWindowLong(hwnd, GWL_STYLE);BOOL bDisable= *(pParam->pChangeStatus);CArray<UINT, UINT> &arr = *(pParam->pArrayExcludeID);CArray<HWND, HWND> &aChanged = *(pParam->pStatusChangedWND);for (int i=0; i!=arr.GetCount(); ++i){if (GetDlgCtrlID(hwnd) == arr[i]) return TRUE;}TCHAR szClsName[512] = {_T('\0')};GetClassName(hwnd, szClsName, 512);if (!_tcscmp(szClsName, _T("Internet Explorer_Server")))//不处理Web浏览器return TRUE;if (!_tcscmp(szClsName, _T("Static"))) //静态文本return TRUE;if (bDisable){if ((lStyle&WS_DISABLED) != WS_DISABLED) {lStyle |= WS_DISABLED;aChanged.Add(hwnd);}} else {if ((lStyle&WS_DISABLED) == WS_DISABLED) {int i = 0;for (; i!=aChanged.GetCount(); ++i){if (hwnd == aChanged[i])break;}if (i == aChanged.GetCount()) {//未在已处理过的控件列表中return TRUE;}aChanged.RemoveAt(i);lStyle &= ~WS_DISABLED;}}SetWindowLong(hwnd, GWL_STYLE, lStyle);::InvalidateRect(hwnd, NULL, TRUE);return TRUE;}};stEnumChild param;param.pChangeStatus= &m_bDisabled;param.pArrayExcludeID= &m_aExcludeIDs;param.pStatusChangedWND = &m_aStatusChangedChild;m_bDisabled = !m_bDisabled;EnumChildWindows(m_hwndParent, CEnumChildHelper::EnumChildProc, (LPARAM)¶m);}void AddExcludeCtrlIDs(UINT nID, ...)//以-1结尾{va_list arglst;va_start(arglst, nID);while (nID != (UINT)-1){//防止添加多次for (INT_PTR i=0; i!=m_aExcludeIDs.GetSize(); ++i){if (nID == m_aExcludeIDs[i]) goto Next;}m_aExcludeIDs.Add(nID);Next:nID = va_arg(arglst, UINT);}va_end(arglst);}private:HWNDm_hwndParent;CArray<UINT, UINT>  m_aExcludeIDs;BOOLm_bDisabled;CArray<HWND, HWND>m_aStatusChangedChild;};class CAutoWndStatusSwitch//自动转换窗口使能与禁用状态{public://ID 以-1结尾CAutoWndStatusSwitch(HWND hwndParent, UINT nID=-1, ...): m_hwndParent(hwndParent), m_bSwitched(FALSE){ASSERT(hwndParent != NULL);AddCtrls(nID);}~CAutoWndStatusSwitch(){if (m_bSwitched)SwitchStatus();}void AddCtrls(UINT nID, ...)//以-1结尾{va_list arglst;va_start(arglst, nID);while (nID != (UINT)-1){//防止添加多次for (INT_PTR i=0; i!=m_aIDs.GetSize(); ++i){if (nID == m_aIDs[i]) goto Next;}m_aIDs.Add(nID);Next:nID = va_arg(arglst, UINT);}va_end(arglst);}void SwitchStatus()//状态转换{m_bSwitched = !m_bSwitched;for (INT_PTR i=0; i!=m_aIDs.GetSize(); ++i){HWND hCtrl = GetDlgItem(m_hwndParent, m_aIDs[i]);if (!IsWindow(hCtrl)) continue;LONG lStyle = GetWindowLong(hCtrl, GWL_STYLE);if ((lStyle&WS_DISABLED) == WS_DISABLED)lStyle &= ~WS_DISABLED;elselStyle |= WS_DISABLED;SetWindowLong(hCtrl, GWL_STYLE, lStyle);::InvalidateRect(hCtrl, NULL, TRUE);}}private:HWNDm_hwndParent;CArray<UINT, UINT>  m_aIDs;BOOLm_bSwitched;};class CAutoHideShowWnd//自动隐藏窗口{public:CAutoHideShowWnd(HWND hWnd, BOOL bHide=TRUE):m_hWnd(hWnd){ASSERT(IsWindow(hWnd));if (bHide) Hide();}~CAutoHideShowWnd(){Restore();}void Hide(){if (IsWindow(m_hWnd) &&(GetWindowLong(m_hWnd, GWL_STYLE) & WS_VISIBLE)) {ShowWindow(m_hWnd, SW_HIDE);}}void Restore(){if (IsWindow(m_hWnd) &&(GetWindowLong(m_hWnd, GWL_STYLE) & ~WS_VISIBLE)) {ShowWindow(m_hWnd, SW_SHOW);}}private:HWND m_hWnd;};}

0 0
原创粉丝点击