* NamedPoint.h

#ifndef NamedPoint_h
#define NamedPoint_h

struct NamedPoint;
typedef struct NamedPoint NamedPoint;

NamedPoint *makeNamedPoint(double x, double y, char *name);
void setName(NamedPoint *np, char *name);
char *getName(NamedPoint *np);

#endif /* NamedPoint_h */

* NamedPoint.c

#include "NamedPoint.h"
#include <stdlib.h>

struct NamedPoint {
    double x, y;
    char *name;
};

NamedPoint *makeNamedPoint(double x, double y, char *name) {
    NamedPoint *p = (NamedPoint *)malloc(sizeof(NamedPoint));
    p->x = x;
    p->y = y;
    p->name = name;
    return p;
}

void setName(NamedPoint *np, char *name) {
    np->name = name;
}

char *getName(NamedPoint *np) {
    return np->name;
}

* point.h

#ifndef point_h
#define point_h

struct mypoint;
typedef struct mypoint MyPoint;

MyPoint *makePoint(double x, double y);
double distance(MyPoint *p1, MyPoint *p2);

#endif /* point_h */

* point.c

#include "point.h"
#include <stdlib.h>
#include <math.h>

struct mypoint {
    double x;
    double y;
};

MyPoint *makePoint(double x, double y) {
    MyPoint *p = (MyPoint *)malloc(sizeof(MyPoint));
    p->x = x;
    p->y = y;
    return p;
}

double distance(MyPoint *p1, MyPoint *p2) {
    double dx = p1->x - p2->x;
    double dy = p1->y - p2->y;
    return sqrt(dx*dx + dy*dy);
}

* main.c

#include "point.h"
#include "NamedPoint.h"
#include <stdio.h>

int main(int argc, const char * argv[]) {

    NamedPoint *origin = makeNamedPoint(0.0, 0.0, "origin");
    NamedPoint *upperRight = makeNamedPoint(1.0, 1.0, "upperRight");
    
    printf("%s <-> %s distance=%f\n",
           getName(origin), getName(upperRight),
           distance((MyPoint *)origin, (MyPoint *)upperRight));
    
    return 0;
}

* test:

origin <-> upperRight distance=1.414214

Program ended with exit code: 0

 

main函数,这里的NamedPoint数据结构是被当作MyPoint数据结构的一个衍生体来使用的。

因为NamedPoint结构体的前2个成员的顺序与MyPoint结构体完全一致,这样实现单继承。

 

必须强制将NamedPoint的参数类型转换为MyPoint, 而在真正的面向对象编程语言中,这种向上转换

通常应该是隐性的。

--------------------------  嵌套父类 -------------------------------------

 

* shape.h

#ifndef shape_h
#define shape_h

typedef short int16_t;
/* Shape's attributes... */
typedef struct {
    int16_t x; /* x-coordinate of Shape's position */
    int16_t y; /* y-coordinate of Shape's position */
} Shape;

/* Shape's operations (Shape's interface)... */
void Shape_ctor(Shape * const me, int16_t x, int16_t y);
void Shape_moveBy(Shape * const me, int16_t dx, int16_t dy);
int16_t Shape_getX(Shape * const me);
int16_t Shape_getY(Shape * const me);

#endif /* shape_h */

* shape.c

#include "shape.h"

void Shape_ctor(Shape * const me, int16_t x, int16_t y) {
    me->x = x;
    me->y = y;
}
void Shape_moveBy(Shape * const me, int16_t dx, int16_t dy) {
    me->x += dx;
    me->y += dy;
}
int16_t Shape_getX(Shape * const me) {
    return me->x;
}
int16_t Shape_getY(Shape * const me) {
    return me->y;
}

* rect.h

#ifndef rect_h
#define rect_h

#include "shape.h" /* the base class interface */
typedef unsigned short uint16_t;
/* Rectangle's attributes... */
typedef struct {
    Shape super; /* <== inherits Shape */
    /* attributes added by this subclass... */
    uint16_t width;
    uint16_t height;
} Rectangle;

/* constructor prototype */
void Rectangle_ctor(Rectangle * const me, int16_t x, int16_t y,
                    uint16_t width, uint16_t height);

#endif /* rect_h */

* rect.c

#include "rect.h"

/* constructor implementation */
void Rectangle_ctor(Rectangle * const me, int16_t x, int16_t y,
                    uint16_t width, uint16_t height) {
    /* first call superclass’ ctor */
    Shape_ctor(&me->super, x, y);
    /* next, you initialize the attributes added by this subclass... */
    me->width = width;
    me->height = height;
}

* main.c

#include <stdio.h>
#include "rect.h"

int main(int argc, const char * argv[]) {
    Rectangle r1, r2; /* multiple instances of Rect */
    /* instantiate rectangles... */
    Rectangle_ctor(&r1, 0, 2, 10, 15);
    Rectangle_ctor(&r2, -1, 3, 5, 8);
    
    printf("Rect r1(x=%d,y=%d,width=%d,height=%d)\n",
           r1.super.x, r1.super.y, r1.width, r1.height);
    printf("Rect r2(x=%d,y=%d,width=%d,height=%d)\n",
           r2.super.x, r2.super.y, r2.width, r2.height);
    
    /* re-use inherited function from the superclass Shape...*/
    Shape_moveBy((Shape *)&r1, -2, 3);
    Shape_moveBy(&r2.super, 2, -1);
    
    printf("Rect r1(x=%d,y=%d,width=%d,height=%d)\n",
           r1.super.x, r1.super.y, r1.width, r1.height);
    printf("Rect r2(x=%d,y=%d,width=%d,height=%d)\n",
           r2.super.x, r2.super.y, r2.width, r2.height);
    
    return 0;
}

* run:

Rect r1(x=0,y=2,width=10,height=15)

Rect r2(x=-1,y=3,width=5,height=8)

Rect r1(x=-2,y=5,width=10,height=15)

Rect r2(x=1,y=2,width=5,height=8)

Program ended with exit code: 0

C语言实现单继承 (inheritance)_#include

 

上一篇: C语言的封装性

https://blog.csdn.net/fareast_mzh/article/details/86775270