【说明】建造模式的C语言实现,改写自http://blog.youkuaiyun.com/sx_wpc/article/details/7659179一文的代码。
【代码清单】
typedef.h
#ifndef __TYPEDEF_H__
#define __TYPEDEF_H__
#include <stdio.h>
#include <stdlib.h>
#ifdef __cplusplus
extern "C" {
#endif
typedef enum _Ret
{
RET_OK,
RET_FAIL
}Ret;
#define return_if_fail(p)\
if(!(p)){\
printf("%s:%d Warning:"#p"Failed\n",__func__,__LINE__);\
return;}
#define return_val_if_fail(p, ret)\
if(!(p)){\
printf("%s:%d Warning:"#p"Failed\n",__func__,__LINE__);\
return (ret);}
#define SAFE_FREE(p) if(p != NULL){free(p); p = NULL;}
#ifdef __cplusplus
}
#endif
#endif
personbuilder.h
#ifndef __PERSONBUILDER_H__
#define __PERSONBUILDER_H__
#include "typedef.h"
#ifdef __cplusplus
extern "C" {
#endif
enum PersonSize
{
P_WIDTH = 21,
P_HEIGHT = 12
};
struct _PersonBuilder;
typedef struct _PersonBuilder PersonBuilder;
struct _PersonBuilder
{
char element[P_HEIGHT][P_WIDTH];
void (*build_head)(void *pPersonBuilder);
void (*build_body)(void *pPersonBuilder);
void (*build_arm_left)(void *pPersonBuilder);
void (*build_arm_right)(void *pPersonBuilder);
void (*build_leg_left)(void *pPersonBuilder);
void (*build_leg_right)(void *pPersonBuilder);
void (*person_display)(void *pPersonBuilder);
void (*destroy)(void *pBuilder);
};
static inline void build_head(PersonBuilder *thiz)
{
return_if_fail(thiz != NULL);
if(thiz->build_head != NULL)
{
thiz->build_head(thiz);
}
}
static inline void build_body(PersonBuilder *thiz)
{
return_if_fail(thiz != NULL);
if(thiz->build_body != NULL)
{
thiz->build_body(thiz);
}
}
static inline void build_arm_left(PersonBuilder *thiz)
{
return_if_fail(thiz != NULL);
if(thiz->build_arm_left != NULL)
{
thiz->build_arm_left(thiz);
}
}
static inline void build_arm_right(PersonBuilder *thiz)
{
return_if_fail(thiz != NULL);
if(thiz->build_arm_right != NULL)
{
thiz->build_arm_right(thiz);
}
}
static inline void build_leg_left(PersonBuilder *thiz)
{
return_if_fail(thiz != NULL);
if(thiz->build_leg_left != NULL)
{
thiz->build_leg_left(thiz);
}
}
static inline void build_leg_right(PersonBuilder *thiz)
{
return_if_fail(thiz != NULL);
if(thiz->build_leg_right != NULL)
{
thiz->build_leg_right(thiz);
}
}
static inline void person_display(PersonBuilder *thiz)
{
return_if_fail(thiz != NULL);
if(thiz->person_display != NULL)
{
thiz->person_display(thiz);
}
}
static inline void person_destroy(PersonBuilder *thiz)
{
return_if_fail(thiz != NULL);
if(thiz->destroy != NULL)
{
thiz->destroy(thiz);
}
}
#ifdef __cplusplus
}
#endif
#endif
thinbuilder.h
#ifndef __THINBUILDER_H__
#define __THINBUILDER_H__
#include "personbuilder.h"
#ifdef __cplusplus
extern "C" {
#endif
struct _ThinBuilder;
typedef struct _ThinBuilder ThinBuilder;
struct _ThinBuilder
{
PersonBuilder person;
};
ThinBuilder *thin_builder_create(void);
#ifdef __cplusplus
}
#endif
#endif
thinbuilder.c
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "thinbuilder.h"
static void thin_build_head(void *pThinBuilder)
{
strcpy(((ThinBuilder *)pThinBuilder)->person.element[0], " ");
strcpy(((ThinBuilder *)pThinBuilder)->person.element[1], " |~~| ");
strcpy(((ThinBuilder *)pThinBuilder)->person.element[2], " |__| ");
strcpy(((ThinBuilder *)pThinBuilder)->person.element[3], " || ");
}
static void thin_build_body(void *pThinBuilder)
{
strcpy(((ThinBuilder *)pThinBuilder)->person.element[4], " |~~| ");
strcpy(((ThinBuilder *)pThinBuilder)->person.element[5], " | | ");
strcpy(((ThinBuilder *)pThinBuilder)->person.element[6], " | | ");
strcpy(((ThinBuilder *)pThinBuilder)->person.element[7], " |__| ");
}
static void thin_build_arm_left(void *pThinBuilder)
{
strncpy(((ThinBuilder *)pThinBuilder)->person.element[4], " ||-", 8);
strncpy(((ThinBuilder *)pThinBuilder)->person.element[5], " || ", 8);
strncpy(((ThinBuilder *)pThinBuilder)->person.element[6], " || ", 8);
strncpy(((ThinBuilder *)pThinBuilder)->person.element[7], " || ", 8);
}
static void thin_build_arm_right(void *pThinBuilder)
{
strncpy(((ThinBuilder *)pThinBuilder)->person.element[4] + 12, "-||", 3);
strncpy(((ThinBuilder *)pThinBuilder)->person.element[5] + 12, " ||", 3);
strncpy(((ThinBuilder *)pThinBuilder)->person.element[6] + 12, " ||", 3);
strncpy(((ThinBuilder *)pThinBuilder)->person.element[7] + 12, " ||", 3);
}
static void thin_build_leg_left(void *pThinBuilder)
{
strncpy(((ThinBuilder *)pThinBuilder)->person.element[8], " //", 10);
strncpy(((ThinBuilder *)pThinBuilder)->person.element[9], " // ", 10);
strncpy(((ThinBuilder *)pThinBuilder)->person.element[10], " // ", 10);
strncpy(((ThinBuilder *)pThinBuilder)->person.element[11], " // ", 10);
}
static void thin_build_leg_right(void *pThinBuilder)
{
strcpy(((ThinBuilder *)pThinBuilder)->person.element[8] + 10, "\\\\ ");
strcpy(((ThinBuilder *)pThinBuilder)->person.element[9] + 10, " \\\\ ");
strcpy(((ThinBuilder *)pThinBuilder)->person.element[10] + 10, " \\\\ ");
strcpy(((ThinBuilder *)pThinBuilder)->person.element[11] + 10, " \\\\ ");
}
static void thin_display(void *pThinBuilder)
{
ThinBuilder *temp = pThinBuilder;
int i;
for(i = 0; i < P_HEIGHT; i++)
{
printf(" %s\n", temp->person.element[i]);
}
}
static void thin_destroy(void *thiz)
{
if(thiz != NULL)
{
SAFE_FREE(thiz);
}
}
ThinBuilder *thin_builder_create(void)
{
ThinBuilder *thiz = malloc(sizeof(ThinBuilder));
if(thiz != NULL)
{
thiz->person.build_head = thin_build_head;
thiz->person.build_body = thin_build_body;
thiz->person.build_arm_left = thin_build_arm_left;
thiz->person.build_arm_right = thin_build_arm_right;
thiz->person.build_leg_left = thin_build_leg_left;
thiz->person.build_leg_right = thin_build_leg_right;
thiz->person.person_display = thin_display;
thiz->person.destroy = thin_destroy;
}
return thiz;
}
fatbuilder.h
#ifndef __FATBUILDER_H__
#define __FATBUILDER_H__
#include "personbuilder.h"
#ifdef __cplusplus
extern "C" {
#endif
struct _FatBuilder;
typedef struct _FatBuilder FatBuilder;
struct _FatBuilder
{
PersonBuilder person;
};
FatBuilder *fat_builder_create(void);
#ifdef __cplusplus
}
#endif
#endif
fatbuilder.c
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "fatbuilder.h"
static void fat_build_head(void *pFatBuilder)
{
strcpy(((FatBuilder *)pFatBuilder)->person.element[0], " ");
strcpy(((FatBuilder *)pFatBuilder)->person.element[1], " |~~~~| ");
strcpy(((FatBuilder *)pFatBuilder)->person.element[2], " |____| ");
strcpy(((FatBuilder *)pFatBuilder)->person.element[3], " | | ");
}
static void fat_build_body(void *pFatBuilder)
{
strcpy(((FatBuilder *)pFatBuilder)->person.element[4], " |~~~~| ");
strcpy(((FatBuilder *)pFatBuilder)->person.element[5], " | | ");
strcpy(((FatBuilder *)pFatBuilder)->person.element[6], " | | ");
strcpy(((FatBuilder *)pFatBuilder)->person.element[7], " |____| ");
}
static void fat_build_arm_left(void *pFatBuilder)
{
strncpy(((FatBuilder *)pFatBuilder)->person.element[4], " |~|~", 7);
strncpy(((FatBuilder *)pFatBuilder)->person.element[5], " | | ", 7);
strncpy(((FatBuilder *)pFatBuilder)->person.element[6], " | | ", 7);
strncpy(((FatBuilder *)pFatBuilder)->person.element[7], " | | ", 7);
}
static void fat_build_arm_right(void *pFatBuilder)
{
strncpy(((FatBuilder *)pFatBuilder)->person.element[4] + 13, "~|~|", 4);
strncpy(((FatBuilder *)pFatBuilder)->person.element[5] + 13, " | |", 4);
strncpy(((FatBuilder *)pFatBuilder)->person.element[6] + 13, " | |", 4);
strncpy(((FatBuilder *)pFatBuilder)->person.element[7] + 13, " | |", 4);
}
static void fat_build_leg_left(void *pFatBuilder)
{
strncpy(((FatBuilder *)pFatBuilder)->person.element[8], " / /", 10);
strncpy(((FatBuilder *)pFatBuilder)->person.element[9], " / / ", 10);
strncpy(((FatBuilder *)pFatBuilder)->person.element[10], " / / ", 10);
strncpy(((FatBuilder *)pFatBuilder)->person.element[11], " / / ", 10);
}
static void fat_build_leg_right(void *pFatBuilder)
{
strcpy(((FatBuilder *)pFatBuilder)->person.element[8] + 10, "\\ \\ ");
strcpy(((FatBuilder *)pFatBuilder)->person.element[9] + 10, " \\ \\ ");
strcpy(((FatBuilder *)pFatBuilder)->person.element[10] + 10, " \\ \\ ");
strcpy(((FatBuilder *)pFatBuilder)->person.element[11] + 10, " \\ \\ ");
}
static void fat_display(void *pFatBuilder)
{
FatBuilder *temp = pFatBuilder;
int i;
for(i = 0; i < P_HEIGHT; i++)
{
printf(" %s\n", temp->person.element[i]);
}
}
static void fat_destroy(void *thiz)
{
if(thiz != NULL)
{
SAFE_FREE(thiz);
}
}
FatBuilder *fat_builder_create(void)
{
FatBuilder *thiz = malloc(sizeof(FatBuilder));
if(thiz != NULL)
{
thiz->person.build_head = fat_build_head;
thiz->person.build_body = fat_build_body;
thiz->person.build_arm_left = fat_build_arm_left;
thiz->person.build_arm_right = fat_build_arm_right;
thiz->person.build_leg_left = fat_build_leg_left;
thiz->person.build_leg_right = fat_build_leg_right;
thiz->person.person_display = fat_display;
thiz->person.destroy = fat_destroy;
}
return thiz;
}
builderclient.h
#ifndef __BUILDERCLIENT_H__
#define __BUILDERCLIENT_H__
#include "personbuilder.h"
#ifdef __cplusplus
extern "C" {
#endif
struct _BuilderClient;
typedef struct _BuilderClient BuilderClient;
struct _BuilderClient
{
PersonBuilder *builder;
};
void set_builder(BuilderClient *thiz, PersonBuilder *builder);
void person_create(BuilderClient *thiz);
#ifdef __cplusplus
}
#endif
#endif
builderclient.c
#include <stdio.h>
#include <stdlib.h>
#include "builderclient.h"
void set_builder(BuilderClient *thiz, PersonBuilder *builder)
{
thiz->builder = builder;
return ;
}
void person_create(BuilderClient *thiz)
{
return_if_fail(thiz != NULL);
thiz->builder->build_head(thiz->builder);
thiz->builder->build_body(thiz->builder);
thiz->builder->build_arm_left(thiz->builder);
thiz->builder->build_arm_right(thiz->builder);
thiz->builder->build_leg_left(thiz->builder);
thiz->builder->build_leg_right(thiz->builder);
}
test.c
#include <stdio.h>
#include <stdlib.h>
#include "builderclient.h"
#include "thinbuilder.h"
#include "fatbuilder.h"
int main(int argc, char **argv)
{
BuilderClient *client = malloc(sizeof(BuilderClient));
PersonBuilder *builder = (PersonBuilder *)thin_builder_create();
set_builder(client, builder);
person_create(client);
person_display(builder);
person_destroy(builder);
return 0;
}
Makefile
exe:=test
temp := $(wildcard test *~)
all:test.c personbuilder.h thinbuilder.h thinbuilder.c fatbuilder.h fatbuilder.c builderclient.h builderclient.c typedef.h
gcc -g $^ -o $(exe)
clean:
rm $(temp)
【源码下载】
*欢迎纠错,共同进步!
转载请标明出处,仅供学习交流,勿用于商业目的
Copyright @ http://blog.youkuaiyun.com/tandesir