上集对OOSM宏包及其应用作了直观的介绍,下面我们来看看ccirc/crect/csqua等对象具体的描述方式。
接口(interface)对行为进行抽象,利用它可以实现类的多态性,imeas.h定义了一个测量周长和面积的接口:
#ifndef __IMEAS_H__ #define __IMEAS_H__ #include "oosm.h" /* Measuring Interface, for measuring the perimeter and area of objects */ interface(imeas) { double (*peri)(void* this); /* for measuring the perimeter of objects */ double (*area)(void* this); /* for measuring the area of objects */ }; #endif/*__IMEAS_H__*/
由于接口是抽象的,所以特别注意把this指针声明为void*类型,这样在进行指针转换的时候会比较方便。
类(class)拥有属性和方法,多态方法采用实现接口的方式来达成目的,crect.h/crect.c定义和实现了一个矩形类:
#ifndef __CRECT_H__ #define __CRECT_H__ #include "imeas.h" /* Rectangle Class, for describing rectangle objects */ class(crect) { implements(imeas); /* Implements imeas interface */ double width; double height; }; #endif/*__CRECT_H__*/
#include "crect.h" static double peri(void* this) { return 2 * (((crect*)this)->width + ((crect*)this)->height); } static double area(void* this) { return ((crect*)this)->width * ((crect*)this)->height; } constructor(crect) { mapping(imeas.peri, peri); mapping(imeas.area, area); } destructor(crect) { return 1; /* Returns 1 for freeing the memory */ }
矩形类构造(constructor)时主要是进行方法的映射,这里实现的是接口imeas中的方法,所以特别注意映射时写成imeas.peri/imeas.area,构造后会自动生成crect_new宏函数。析构(destructor)中可以先释放内部的空间后再返回1删除自身,析构后会自动生成crect_delete宏函数。
同样的,ccir.h/ccir.c定义是实现了圆形类:
#ifndef __CCIRC_H__ #define __CCIRC_H__ #include "imeas.h" /* Circle Class, for describing circular objects */ class(ccirc) { implements(imeas); /* Implements imeas interface */ double radius; double (*diam)(ccirc* this); /* for measuring the diameter of the circular objects */ }; #endif/*__CCIRC_H__*/
#include "ccirc.h" #define PI (3.1415926) static double peri(void* this) { return 2 * PI * ((ccirc*)this)->radius; } static double area(void* this) { return PI * ((ccirc*)this)->radius * ((ccirc*)this)->radius; } static double diam(ccirc* this) { return 2 * this->radius; } constructor(ccirc) { mapping(imeas.peri, peri); mapping(imeas.area, area); mapping(diam, diam); } destructor(ccirc) { return 1; /* Returns 1 for freeing the memory */ }圆形类在实现imeas接口的基础上,另有自己的diam方法,注意自己本身方法直接映射即可。