设为首页 加入收藏

TOP

C与泛型 (二)
2014-11-23 23:39:57 来源: 作者: 【 】 浏览:43
Tags:
t.i
gcc -g -S printtest.i -o printtest.s
printtest.i:$(SRC)
gcc -g -E $(SRC) -o printtest.i
clean:
rm *~ *.o *.s *.i $(TARGET)
*此处为了观察代码的编译、汇编、链接过程,Makefile稍显复杂,可直接用下述指令编译

[html] view plaincopyprint gcc printtest.c -o printtest

gcc printtest.c -o printtest

【运行结果】

[html]
**************** Integer Test ****************
0123456789
**************** Integer Test ****************
0123456789
**************** Float Test ****************
2.600000
**************** String Test ****************
Generics test!

**************** Integer Test ****************
0123456789
**************** Integer Test ****************
0123456789
**************** Float Test ****************
2.600000
**************** String Test ****************
Generics test!


上述代码,有一处值得注意,在定义时,提供了两种print_int函数:

[html]
static int print_int(void *data)
{
printf("%d", (int)data);

return RET_OK;
}

static int print_int2(void *data)
{
printf("%d", *(int*)data);

return RET_OK;
}

static int print_int(void *data)
{
printf("%d", (int)data);

return RET_OK;
}

static int print_int2(void *data)
{
printf("%d", *(int*)data);

return RET_OK;
}调用时:

[html]
int i = 0;

int *pi = &i;

PRINTSTAT( "%s", "Integer")
for(; i<10; i++)
print(print_int, (void *)i);
printf("\n");

PRINTSTAT( "%s", "Integer")
for(i = 0; i<10; i++)
print(print_int2, (void *)pi);
printf("\n");

int i = 0;

int *pi = &i;

PRINTSTAT( "%s", "Integer")
for(; i<10; i++)
print(print_int, (void *)i);
printf("\n");

PRINTSTAT( "%s", "Integer")
for(i = 0; i<10; i++)
print(print_int2, (void *)pi);
printf("\n");
调用print_int时,将int类型强制转换为void *类型;调用print_int2时,将int *类型强制转化为void *类型。令人惊讶的是,上述两种方法,都能输出正确结果。其实,print_int提供的方法只是凑巧而已,因为int是4字节,而void *类型也是4字节,强制转换居然没有发生错误!但如果是float类型,再利用print_int类似的方法就不行了,gcc提示无法进行转换。安全的方式是将int *转换为void *,再在print_int处理函数中将void *转换为int *,然后解引用。

2 采用“#”

方法1提供的代码中,已经看出了“#”的威力。下面看看泛型的另一种实现:

【代码清单】

printtest.h

[html]
#ifndef __PRINTTEST_H__
#define __PRINTTEST_H__

#define GNERIC_PRINT(TYPE,FORMAT,SUFFIX) \
int print##SUFFIX( TYPE data )\
{\
printf(FORMAT, data);\
return 0;\
}

#endif

#ifndef __PRINTTEST_H__
#define __PRINTTEST_H__

#define GNERIC_PRINT(TYPE,FORMAT,SUFFIX) \
int print##SUFFIX( TYPE data )\
{\
printf(FORMAT, data);\
return 0;\
}

#endif

printtest.c

[html]
#include
#include
#include "printtest.h"

#define DEBUG 0

#define PRINTSTAT( FORMAT, STAT) \
printf("**************** " FORMAT " Test ****************\n"\
,STAT);

#define DEBUG_PRINT(FORMAT, VALUE) printf("File %s line %d: "\
#VALUE " = " FORMAT "\n"\
,__FILE__, __LINE__,VALUE\
);

enum {
RET_OK,
RET_FAIL
};

GNERIC_PRINT(int, "%d", _int)
GNERIC_PRINT(float, "%f", _float)
GNERIC_PRINT(char *, "%s", _str)

int main(void)
{
int i = 0;
float f = 2.6;
char *test = "Generics test!";

#if DEBUG
DEBUG_PRINT("%f", f)
#endif

PRINTSTAT( "%s", "Integer")
for(; i<10; i++)
print_int(i);
printf("\n");

PRINTSTAT( "%s", "Float")
print_float(f);
printf("\n");

PRINTSTAT( "%s", "String")
print_str(test);
printf("\n");

return RET_OK;
}

#include
#include
#include "printtest.h"

#define DEBUG 0

#define PRINTSTAT( FORMAT, STAT) \
printf("**************** " FORMAT " Test ****************\n"\
,STAT);

#define DEBUG_PRINT(FORMAT, V

首页 上一页 1 2 3 下一页 尾页 2/3/3
】【打印繁体】【投稿】【收藏】 【推荐】【举报】【评论】 【关闭】 【返回顶部
分享到: 
上一篇将e插入到顺序表的适当位置上以保.. 下一篇C语言批量下载文件(含源码)

评论

帐  号: 密码: (新用户注册)
验 证 码:
表  情:
内  容: