Oh,shit.终于把MFC运行机制看完了,等明天写完下部分,就可以开始真正的写MFC了。
是不是很落伍??。。。
我发现我学习Windows编程的方法和别人是不一样的。
我先学的C,C++,然后再学C++(C++编程思想),然后再学C++(C++编程思想),然后学了Windows程序设计(60RMB)的前两章,发现很迷惑,然后就去学Linux内核(将近90RMB),发现看不懂,然后去学Win32汇编(当时正好在学病毒,正好要用),于是狠下心(80RMB)买了罗云宾老师的汇编,发现买对了,虽然可能不会用到,但绝对是一本入门的经典。在考完试后的寒假里我一口气把书读完,很高兴,以为自己很NB,结果再写c++程序时发现出问题了,不会写C了,我要写一个a = b,居然想写mov b,a!!然后最严重的问题是类型转化的问题。汇编中没有什么类型的概念,全部都视为DWORD,但是在C/C++这种高级语言中就成了很严重的问题,C++尤为严重,因为他的类型检查非常的强烈!!
然后又去读Linux源码,读了十几天,发现又会了不少。
然后去学C++设计模式,那可不是简单的东西,学了很长时间就看会了Factory和AbstractFactory模式!
写了两个ACM程序,回学校后又开始学MFC,静下心来看完MFC简约的代码,终于明白了。。。
原来,Windows的世界是这个样子的,以后再也不怕MFC了。
虽然MFC已经陈旧,而且其封装等非常的ugly(最烦那长长的名称,讨厌XXXX命名法,虽然很好用),但是对自己来说是一种提高。尤其是当别人会MFC时你不会,什么感受??而且他的各种机制以及编程的思想和技巧是非常值得学习的。
虽然我已经将C++编程思想看过n回了,但是还是觉得c++掌握的不好,尤其是在看C++设计模式和看STL的源码是发现还是有很多看不懂。。。所以我又借来(学校图书馆)C++ Primer,还得再看看,深刻了解之。。。
下面附上今天下午学习的源码,晚上学的那些没写代码,明天再写吧。
#ifndef _AFXCOLL_H_ #define _AFXCOLL_H_ #include "_afxwin.h" #include "_afxplex.h" class CMapPtrToPtr { public: CMapPtrToPtr(int nBlockSize = 10 /* = 10 */); ~CMapPtrToPtr(); int GetCount() const; BOOL IsEmpty() const; BOOL Lookup(void* key, void*& rValue); void*& operator[](void* key); void SetAt(void* key, void* newValue); BOOL RemoveKey(void* key); void RemoveAll(); UINT GetHashTableSize() const; void InitHashTable(UINT hashSize, BOOL bAllocNow = TRUE /* = TRUE */); UINT HashKey(void* key) const; //声明为常成员函数有什么作用来?我忘了 protected: struct CAssoc { CAssoc* pNext; void* key; void* value; }; struct CPlex* m_pBlocks; //保存内存块首地址 int m_nBlockSize;//每个块可以容纳的CAssoc数目 CAssoc* m_pFreeList;//预留空间中没有被使用的第一个指针 int m_nCount;//记录程序中一共使用的CAssoc个数 CAssoc* NewCAssoc();//new一个CAssoc,怎样让他使用CPlex空间呢? void FreeCAssoc(); CAssoc** m_pHashTable; int m_nHashTableSize; CAssoc* GetAssocAt(void* key, UINT& nHash) const; private: }; inline int CMapPtrToPtr::GetCount() const { return m_nCount; } inline BOOL CMapPtrToPtr::IsEmpty() const{ return m_nCount == 0;} inline void CMapPtrToPtr::SetAt(void* key, void* newValue) { (*this)[key] = newValue;//不是很理解 } inline UINT CMapPtrToPtr::GetHashTableSize() const{ return m_nHashTableSize; } #endif
我就随便贴了,反正只是给自己看
#ifndef _AFXPLEX_H_ #define _AFXPLEX_H_ #include "_afxwin.h" //奇怪,没见到这个头文件啊 struct CPlex { CPlex* pNext;//指向下一个内存块的首地址 void* data() {return this + 1;} static CPlex* Create(CPlex* &pHead,UINT nMax,UINT cbElement); void FreeDataChain(); }; #endif
#ifndef _AFX_H_ #define _AFX_H_ #ifdef _DEBUG #define AfxDebugBreak _asm{ int 3 } #define ASSERT(f) / if(!(f)) AfxDebugBreak(); #define TRACE ::AfxTrace #define VERIFY(f) ASSERT(f) void __cdecl AfxTrace(LPCTSTR lpszFormat, ...); #else #define ASSERT(f) ((void)0) #define VERIFY(f) ((void)(f)) inline void __cdecl AfxTrace(LPCTSTR, ...){} #define TRACE (void)0 #endif//_DEBUG #include <windows.h> class CObject; struct CRuntimeClass { LPCSTR m_lpszClassName;//类名称 int m_nObjectSize;//类大小 UINT m_wSchema;//版本号 CObject* (__stdcall* m_pfnCreateObject)();//创建类函数的指针(注意是创建类,而不是创建对象啊) CRuntimeClass* m_pBaseClass;//其基类的地址 CObject* CreateObject(); BOOL IsDerivedFrom(const CRuntimeClass* pBaseClass) const; CRuntimeClass* m_pNextClass; }; class CObject { public: virtual CRuntimeClass* GetRuntimeClass() const; virtual ~CObject(); BOOL IsKindOf(const CRuntimeClass* pClass) const; static const CRuntimeClass classCObject; protected: private: }; inline CObject::~CObject() {} #define RUNTIME_CLASS(class_name) ((CRuntimeClass*)&class_name::class##class_name) //CRuntimeClass命名规则:在类名前冠以class作为名字,##是告诉编译器,把两个字符串捆绑在一起 /* #define DECLARE_DYNAMIC(class_name)/ public:/ static const CRuntimeClass class##class_name;/ virtual CRuntimeClass* GetRuntimeClass() const; #define IMPLEMENT_RUNTIMECLASS(class_name,base_class_name,wSchema,pfnNew)/ const CRuntimeClass class_name::class##class_name = {/ #class_name,sizeof(class class_name),wSchema,pfnNew,/ RUNTIME_CLASS(base_class_name),NULL};/ CRuntimeClass* class_name::GetRuntimeClass() const/ {/ return RUNTIME_CLASS(class_name);/ }/ //宏写的没什么意思*/ #endif//_AFX_H_
#include <windows.h> #include <stdio.h> #ifdef _DEBUG void __cdecl AfxTrace(LPCTSTR lpszFormat, ...) { va_list args; va_start(args,lpszFormat); char szBuffer[512]; _vsnprintf(szBuffer,512,lpszFormat,args); ::OutputDebugString(szBuffer); va_end(args); } #endif//_DEBUG
CMapPtrToPtr::CAssoc* CMapPtrToPtr::NewAssoc() { if (m_pFreeList == NULL) { CPlex* newBlock = CPlex::Create(m_pBlocks,m_pBlocks,sizeof(CAssoc)); //下面是将新内存块中CAssoc添加到m_pFreeList中 CAssoc* pAssoc = (CAssoc*)newBlock->data(); pAssoc += m_nBlockSize - 1; for(int i = m_nBlockSize - 1 ; i >= 0 ; i-- , pAssoc --){ pAssoc->pNext = m_pFreeList; m_pFreeList = pAssoc; //反向入链 } } CAssoc* pAssoc = m_pFreeList; m_pFreeList = m_pFreeList->pNext; //取出一个CAssoc结构 m_nCount++; //初始化 pAssoc->key = 0; pAssoc->value = 0; return pAssoc; } void CMapPtrToPtr::FreeAssoc(CAssoc* pAssoc){ pAssoc->pNext = m_pFreeList; m_pFreeList = pAssoc; m_nCount--; if (m_nCount == 0) { RemoveAll(); //释放所有空间 } } void CMapPtrToPtr::InitHashTable(UINT hashSize, BOOL bAllocNow /* = TRUE */) { if (m_pHashTable != NULL) { delete []m_pHashTable; m_pHashTable = NULL; } if (bAllocNow) { m_pHashTable = new CAssoc*[hashSize]; memset(m_pHashTable,0,sizeof(CAssoc*)*hashSize); } m_nHashTableSize = hashSize; }
#include "_AFX.H" const struct CRuntimeClass CObject::classCObject = { "CObject",//类名 sizeof(CObject),//大小 0xffff,//无版本号 NULL,//不支持动态创建 NULL,//没有基类 NULL }; CRuntimeClass* CObject::GetRuntimeClass() const{ return RUNTIME_CLASS(CObject);//这是那个宏,返回动态运行类的名称吧 } BOOL CObject::IsKindOf(const CRuntimeClass* pClass) const{ CRuntimeClass* pClassThis = GetRuntimeClass(); return pClassThis->IsDerivedFrom(pClass); }
#include "_AFXPLEX.H" CPlex* CPlex::Create(CPlex* &pHead,UINT nMax,UINT cbElement){ CPlex* p = (CPlex*) new BYTE[sizeof(CPlex) + nMax * cbElement]; p->pNext = pHead; pHead = p; return p; } void CPlex::FreeDataChain(){ CPlex* p = this; while (p != NULL) { BYTE* pByte = (BYTE*)p; CPlex* pNext = p->pNext; delete []pByte; p = pNext; } }
#include "_AFX.H" #include <iostream> using namespace std; class CPerson:public CObject{ public: virtual CRuntimeClass* GetRuntimeClass() const{ return (CRuntimeClass*)&classCPerson; } static const CRuntimeClass classCPerson; static CObject* __stdcall CreateObject(){ // 这样的话支持运行时动态创建 return new CPerson; } }; const CRuntimeClass CPerson::classCPerson = { "CPerson", sizeof(CPerson), 0xffff, &CPerson::CreateObject,//添加的时候不要加() (CRuntimeClass*)&CObject::classCObject,//这个是他的基类 NULL }; int mian(){ CRuntimeClass* pRuntimeClass = RUNTIME_CLASS(CPerson); CObject *pObject = pRuntimeClass->CreateObject(); delete pObject; CObject* pMyObject = new CPerson;//看到了c++的强大之处,这是其一 if (pMyObject->IsKindOf(RUNTIME_CLASS(CPerson))) { CPerson* pMyPerson = (CPerson*)pMyObject; cout << "a CPerson created!/n"; delete pMyPerson; } else { delete pMyObject; } return 0; }
基础打好了最好了,什么掌握的都非常快,不要迷恋哥。。。
今天早上去图书馆自习看来半章的《Data Mining : Concept & technology》,N人Jiawei Han写的,看起来很迟了。
读课本,英文版的《system anaylz》……老师讲的so 快,我他每将一节课我在下面都得看10小时,才能勉强跟上。。。
晕
这两天老学英语了,各种英语书,还有考研英语。。。
幸好6级过了,要不。。。
该洗脸刷牙睡觉了。