导图社区 面向对象的程序1
关于面向对象的程序1的思维导图,如 将用户自己创建的GDI对象设置到设备环境中需要调用CDC类的成员函数SelectObject。
编辑于2023-06-06 09:41:06 湖北省MFC
mfc画笔的使用方法与步骤
通过CPen类构造函数或者成员函数CreatePen创建画笔对象
然后调用CDC类的成员函数SelectObject将画笔对象设置到设备环境中去,同时记录设备环境缺省的画笔对象指针
画笔对象使用完毕后还要调用selectobject函数恢复设备环境原有的画笔对象指针
将用户自己创建的GDI对象设置到设备环境中需要调用CDC类的成员函数SelectObject
在MFC应用程序中调用函数AFXGetMainWnd可获得应用程序的活动主窗口指针,返回这个指针的类型为CWnd*
在MFC中调用创建模态对话框需要调用函数DoModal ,如果该函数的返回值是IDOK,说明对话框退出时是点击了“确定”按钮
该函数的返回值代表用户是按哪一个按钮返回的
模态对话框的含义是:即在该对话框关闭之前,其他窗口无法获得焦点
退出模态对话框一般选择响应按钮IDOK或者IDCANCEL的消息函数OnOK,OnCancel
在MFC中显示提示消息使用函数AfxMessageBox
MFC中设备环境类的基类为CDC,所有窗口类的基类为CWnd
主题
在MFC中更新菜单状态的消息是__D____。 a. WM_COMMAND; b. UPDATE; c. INVALIDATE; d. ON_UPDATE_COMMAND_UI
在MFC应用程序中调用函数____B__可获得应用程序对象指针。 a. GetParentFrame; b. AfxGetApp; c. AfxGetMainWnd; d. AfxMessageBox
右键菜单是通过CMenu类及其成员函数在程序运行过程中动态创建的,右键菜单的创建和显示一般在___A___消息响应函数中编程实现。 a. WM_CONTEXTMENU; b. WM_CREATE; c. WM_PAINT; d. ON_UPDATE_COMMAND_UI
DDX:对话框数据交换
编程时如何实现MFC提供的DDX功能
对话框DDX和DDV功能是由DoDataExchange()函数实现的。DDX实现数据交换,DDV实现数据校验
用户不能直接调用DoDataExchange(),而是调用CWnd::UpdataData(Bool)
当调用UpdataData(FALSE)时,MFC通过对话框派生类的函数DoDataExchange()将数据从成员变量传递到关联的控件
当调用UpdataData(TRUE)时,MFC通过调用对话框派生的函数DoDataExchange将数据从控件传递到关联的成员函数
如果要将对话框界面上的输入值更新到相应对话框类的DDX成员变量,应该调用函数UpdataData(TRUE)
DDV:对话框数据校验
SDI,MDI
SDI是MFC中的单文档界面
MDI是MFC中的多文档界面
比较两者异同
文档模板类分别为CSingleDocTemplate和CMutiDocTemplate
框架窗口类分别为CMainFrame和CChirdFrame
初始化时指定的菜单资源ID不一样
在MFC文档视图类应用程序,创建右键菜单功能需要响应消息 WM_CONTEXTMENU ; 如果需要改变或者设置菜单或者工具栏按钮的状态需要响应消息 WM_UPDATE_COMMAND_UI ; 如果需要在框架窗口中创建工具栏并设置工具栏的显示风格,需要响应消息 WM_CREATE ; 如果需要在鼠标左键按下时获取鼠标坐标并作响应的数据处理,需要响应消息 WM_LBUTTONDOWN 。
如果在对话框中初始化控件的显示风格,需要重载类CDialog的虚函数 OnInitDialog ; 如果在文档视图类应用程序中将文档类的数据保存成文件,需要重载类CDocument的虚函数 OnSaveDocument
MFC应用程序中没有main函数,只有一个WinMain函数
MFC把WinMain函数隐藏了,我们在程序里看不到。
程序员能看到的是APP类中的共有成员函数InitInstance,这个函数是CWinAPP中定义的虚函数
MFC从应用程序类的InitInstance开始,到ExitInstance结束
因此,程序员可以在应用程序类的InitInstance函数中添加全局变量的初始化操作,在应用程序类的ExitInstance函数中进行全局内存资源释放工作
常用的鼠标消息
WM_MOUSEMOVE(鼠标移动)
WM_LBUTTONDOWN(左键按下),WM_LBUTTONUP(左键弹起),WM_LBUTTONDBLCLK(双击左键)
WM_RBUTTONDOWN(右键按下),WM_RBOTTONUP(右键弹起),WM_RBUTTONDBLCLK(双击右键)
鼠标消息处理函数一般都有含有两个参数
类型为UINT的参数nFlag代表鼠标按键和键盘上控制键的状态
类型为CPoint的参数point代表鼠标当前所处位置的坐标
三目运算符
(y >= 0) ? y : 0; ? : ; 是c语言中唯一一个三目运算符。如果x大于y为真,结果输送x,否则为假结果输送y;
MFC中的对话框类为CDialog
对话框类中控件和成员变量的初始化可以重载CDialog类中的消息响应函数 OnInitDialog,这个函数的对应的消息为WM_INITDIALOG
在MFC中
文档类的基类是CDocument,是专门为数据处理设计的类
视图类的基类是CView,是专门处理数据显示的类
在视图类中,若要访问文档中的数据,应当首先调用函数GetDocument获得文档对象指针
在文档类中,若要更新视图类中的数据显示,可以调用函数UpdataALLViews
视图是一个没有边框的窗口,CView是CWnd的派生类,它位于框架窗口的客户区。视图不能单独存在,它必须依附于一个框架窗口
在MFC中,应用程序类的基类是CWinAPP
在MFC应用程序中有一个CWinAPP类的派生类的对象theAPP,它是一个全局变量,代表了应用程序的主线程。 它在程序的整个运行期间都是始终存在的,它的销毁也意味着运行程序的消亡
在类成员函数中,如果要寻址类对象本身,需要使用this指针
在类中,如果要将一个成员函数定义为虚函数,需要在函数声明前添加关键字
Windows的绘图坐标系分为
逻辑坐标系
设备坐标系
GDI支持这两种坐标系
在MFC绘图时,设备坐标与逻辑坐标的转换可以使用CDC类的成员函数DPtoLP,LPtoDP
鼠标消息的坐标参数使用客户区坐标/设备坐标
CDC类用于绘图的成员函数使用与客户区坐标对应的逻辑坐标
面向对象的程序设计的四个基本特征是抽象,封装,继承,多态
设计了一个类以后,在程序中通过定义对象来使用类(或者说让类工作)
类通过虚函数来继承多态
纯虚函数的具体语法: class类名{ virtual 函数类型 成员函数名称(函数参数)=0; };
抽象基类CShape中有一个纯虚函数DrawShape,下面的声明方式中____C__是正确的? a.void DrawShape(CDC* pDC = NULL); b.virtual void DrawShape(CDC* pDC){}; c.virtual void DrawShape(CDC* pDC) = 0; d.virtual void DrawShape(CDC* pDC = NULL);
对于任意一个类,析构函数的个数最多为___A___。 a. 1; b. 2; c. 3; d. 任意多
但是构造函数就可以有很多个,可以重载
析构函数不能带任何参数,也没有返回值 构造函数的功能主要用于在类的对象创建时定义初始化的状态。 它没有返回值 ,也不能用void来修饰。
假设 class Y : public X,即类 Y 是类 X 的派生类,则声明一个 Y 类的对象时和删除Y 类对象时 ,调用构造函数和析构函数的次序分别为 X(), Y(), ~Y(), ~X()
假定CStaff为一个类,则执行语句“CStaff a(2), b[3], *p[4];”时调用该类构造函数的次数为 4
假定 CCircle 为一个类,则执行语句“CCircle a(3), b[4], *p[4];”时调用该类构造函数的次数为. 5
下面哪一个类___D___不是MFC中封装的GDI【绘图的】对象类? a. CPen【画笔】; b. CPallete【调色板】; c. CFont【字体】; d. CColorDialog【对话框的颜色】
MFC封装了GDI对象。其中画笔对象类为___CPen_____,画刷对象类为_CBrush_______,字体对象类为_CFont________。CBitmap位图,CPallete【调色板】,CRgn区域
假定CShape是一个类,在main函数中执行下面语句时会调用CShape的构造函数___A___次? CShape** pShape = new CShape *[100]; a. 0; b. 1; c. 2; d. 100
inline void swap(int a, int b) { int t = a; a = b; b = t; } int main() { int x1 = 10, x2 = 20; swap(x1, x2); cout << x1 << x2; }
x1=10, x2=20
.假定一个类的构造函数为"A(int i=4, int j=0) {a=i;b=j}", 则执行"A x (1);”语句后,和的值分别为() A.1和0 B. 1和4 C. 4和0 D. 4和1 答案: A解析:带默认的构造函数,对应实参没有值时就采用形参值。调用构造函数时,i=1,不采用默认值,而只有一个参数, j采用默认值0 即j=0,因此a=1,b=0,选择A项。
假定一个类CPt的构造函数为“CPt(int px=4, int py=0){x = px; y = py;}”,那么执行语句“CPt pt(1);”后,pt.x和pt.y的值分别为 A 。 A. 1,0 B. 1,4 C. 4,0 D. 4,12
假定一个类 CMyPoint 只有一个构造函数,其形式为“ CMyPoint(int px=1, int py=1){x = px; y = py;}”,那么执行语句“CMyPoint* pPoint = new CMyPoint(4);”后,pPoint->x和 pPoint->y 的值分别为__. 4, 1
假定CStaff为一个类,则执行语句“CStaff a(2), b[3], *p[4];”时调用该类构造函数的次数为 4
假设 CImg 是一个类,那么该类的拷贝初始化构造函数的声明语句为 C 。 A. CImg(CImg a); B. CImg&(Img a); C. CImg (CImg& a); D. CImg (Img* p);
文本文件与二进制文件有什么不同
每条数据的长度不同 文本文件每条数据通常是固定长度的。以ASCII为例,每条数据(每个字符)都是1个字节。进制文件每条数据不固定。如short占两个字节,int占四个字节,float占8个字节……
存储形式 二进制文件里存储的东西是二进制数据,就是01串。而文本文件中存储的是字符串
读取的软件不同 文本文件编辑器就可以读写。比如记事本、NotePad++、Vim等。二进制文件需要特别的解码器。比如bmp文件需要图像查看器,rmvb需要播放器……
编程题
编写一个冒泡排序的函数模板,并利用它分别对int型和double型数组进行排序。
#include<iostream> using namespace std; template<class T> void my_Bubble(T* a, int n) { for (int i = 0; i < n - 1; i++) { for (int j = i+ 1; j < n; j++) { if (a[i] > a[j]) { T t = a[j]; a[j] = a[i]; a[i] = t; } } } } void main() { int a[] = { 1,3,4,2,5 }; double b[] = { 1,4.2,3.1,2,5 }; my_Bubble<int>(a, sizeof(a) / sizeof(int)); my_Bubble<double>(b, sizeof(b) / sizeof(double)); for (int i = 0; i < sizeof(a) / sizeof(int); i++) { cout << a[i] << " "; } cout << endl; for (int i = 0; i < sizeof(b) / sizeof(double); i++) { cout << b[i] << " "; } cout << endl; }
CShape是图形的抽象基类,CPolyLine、CPolygon、CEllipse是三个派生类,分别对应折线、多边形和椭圆。请参照下面类CShape和CPolyLine的程序代码,首先实现类CPolygon(不要求实现成员函数DisplayXOR,必须实现成员函数Display)(10分);其次,请说明函数CreateShape的作用(10分)。 #include "MyArray.h" enum SHAPE{ UNKNOWN = -1, POLYLINE, POLYGON, ELLIPSE}; class CShape{ public: CShape(){m_nShapeType = UNKNOWN;}; virtual ~CShape(){}; virtual void Add(POINT point){m_ptArray.Add(point);}; virtual void Display(CDC* pDC) = 0; virtual void DisplayXOR(CDC* pDC, POINT& pt) = 0; SHAPE GetType(){return m_nShapeType;}; POINT* GetPoints(){return m_ptArray.GetData();}; int GetPointNumber(){return m_ptArray.GetSize();}; protected: CMyArray<POINT> m_ptArray; SHAPE m_nShapeType; }; CShape* CreateShape(SHAPE type){ CShape* pShape = NULL; switch (type){ case POLYLINE: pShape = new CPolyLine; break; case POLYGON: pShape = new CPolygon; break; case ELLIPSE: pShape = new CEllipse; break; } return pShape; } #include "Shape.h" class CPolyLine : public CShape{ public: CPolyLine(); virtual ~CPolyLine(); virtual void Display(CDC* pDC){ if (pDC){ POINT* lpPoint = m_ptArray.GetData(); int nPtNum = m_ptArray.GetSize(); pDC->Polyline(lpPoint, nPtNum); } }; virtual void DisplayXOR(CDC* pDC, POINT& pt){ if (pDC){ POINT* lpPoint = m_ptArray.GetData(); int nPtNum = m_ptArray.GetSize(); pDC->Polyline(lpPoint, nPtNum); CPen pen(PS_SOLID, 1, RGB(255, 255, 255)); CPen* pOldPen = pDC->SelectObject(&pen); int op2 = pDC->SetROP2(R2_XORPEN); pDC->MoveTo(lpPoint[nPtNum-1]); pDC->LineTo(pt); pDC->SetROP2(op2); pDC->SelectObject(pOldPen); pen.DeleteObject(); } }; }; class CPolygon :public Cshape { public: CPolygon() { m_nshapeType = POLYGON; }; virtual ~CPolygon() {}; virtual void Display(CDC* pDC) { POINT* lpPoint = m_ptArray.GetData(); int nPtNum = m_ptArray.GetSize(); if (pDC) { pDC->Polygon(lpPoint, nPTNum); } } };
class CPolygon :public Cshape { public: CPolygon() { m_nshapeType = POLYGON; }; virtual ~CPolygon() {}; virtual void Display(CDC* pDC) { POINT* lpPoint = m_ptArray.GetData(); int nPtNum = m_ptArray.GetSize(); if (pDC) { pDC->Polygon(lpPoint, nPTNum); } } };
CreateShape函数用于根据输入的类型创建对应的图形对象,然后返回指向实际对象的基类指针,该函数是动态多态的具体体现