最简单的做法是在结构体里存函数指针,然后初始化结构体的时候将函数的地址赋值给它。
网站建设哪家好,找成都创新互联公司!专注于网页设计、网站建设、微信开发、成都微信小程序、集团企业网站建设等服务项目。为回馈新老客户创新互联还提供了黄南州免费建站欢迎大家使用!
复杂一点的,就得按照c++的多态原理,用虚函数表(其实就是能记录函数名对应的函数地址就好)记录每种结构体的成员函数地址,然后每个结构体里多存一个虚函数表的地址。。。然后调用函数的时候查到函数地址强转成函数类型然后调用。。。这个可以自己研究一下c++的虚函数表机制。
1、先说二维,可以这么理解:
int n[3]有3个int
那么,
int m[5][3]有5个int[3]
赋值时:
n[1]=3把3给1号
m[4]={5,9,4}m[4]是个int[3]类型,这么赋值,也就是这么赋值:
m[4]的[0]是5:m[4][0]=5
m[4][1]=9
m[4][2]=4
懂了吗?三维甚至更多维大同小异,比如
int k[4][5][3]有4个int[5][3]
2、例程:
int*** CreateGrid(int m,int n,int t)
{
int*** tt = NULL;
tt = (int***)malloc(sizeof(int)*m);
for(int i=0;im;i++)
{
tt[i] = (int**)malloc(sizeof(int)*n);;
for (int k=0;kn;k++)
{
tt[i][k] = (int*)malloc(sizeof(int)*t);
}
}
return tt;
}
void FreeGrid(int*** tt,int m,int n,int t)
{
if(tt != NULL)
{
for(int i=0;im;i++)
{
for (int j=0;jn;j++)
{
free((tt[i][j]));
}
free(tt[i]);
}
free(tt);
tt = NULL;
}
}
今天,一个学徒向我提出了问题,说是不管他怎么理解,对于多维数组和多维指针还是不太明白,嗯,耐心的讲解了一番……还好不负所望,他听懂了,不然的话,咱这块老脸可就丢大了:),整理了一下,把今天讲给他听的放到网上来,供遇到同样问题的朋友参考,有理解错误的地方,还请各位高手指点。首先C++为矩形数组,意味着 int[2][3] 等于 int[6],int[2][3][4] 等于 int[24] 那为什么还需要多维数组?一维数组完全能完成多维数组的功能啊。原因是,这是为了方便算法的科学计数吧。就像一千万可以表示为:1000000 也可以表示为 0.1X10的8次方。int a[2] 这是一个一维数组,int *p=a,p是指向这个数组的指针。a存储的是这个数组内存的首地址,也就是说 a 等于 p 等于 数组内存首地址,所以,a[0] 的值等于 *p 等于 首个元素的值。思考,如果现在需要扩充这个数组怎么办呢?我们知道,一维数组a存储的是数组内存的首地址(a[0],a[1] 才是数组元素的值),那如果把 a[0] 的值换成另一个数组的内存首址,那不是就可以扩充这个数组了吗(前面说过C/C++用的是矩形数组,意味着,如果数组a里的任何元素存储了另一个数组的首地址,那么其它元素的存储值也必需是内存首地址)?假设,又定义了两个数组 : int aa[3],ab[3] 把 aa 首地址给a[0] ,把 ab 首地址给 a[1] ,这就形成了“数组的数组” ,即:一个数组内的元素值是了另一个数组的内存首地址,定义方法:int a[2][3],表示:我定义了一个数组,有两个元素,而每个元素的值,存储的是另一个 包含三个元素的 数组内存首地址。要怎么使用?首先,如果要访问上面假设的aa[0] 那么使用 a[0][0] ,要访问 ab[0] 使用 a[1][0] ,好了,下标访问解决了,那这就行了吗?不行,还有指针啊,一维数指可以用指针来操作,那二维数组呢?当然也可以……int a[2] ,是一个一维数组,它存储了两个 int 型。每个 int 型 使用 sizeof(int) 得出,占用四个字节。那么 sizeof(a[0]) 等于4 ,sizeof(a)等于 sizeof(a[0]) 乘以 2 等于 8。也就是说,使用 int 指针,偏移两次(每次4字节),就可以操作这个数组的值。而在 int a[2][3] 里,a[0] 还是占用4字节吗?当然不是,前面说过,它的每个元素包含了另外一个数组,这时候的 a[0] 占用了 sizeof (a[0]) 等于 int (4字节) 乘以 3 等于 12字节……使用 int 型指针 每次++只能偏移 4 个字节,而我们现在需要的是 从 a[0] 偏移到 a[1] --12个字节,那怎么办? int(4字节) 乘以 3,所以定义 int (*p)[3],注意这里,不是使用 int *p[3],而是使用int (*p)[3],为什么要个括号?因为,int *p[3],定义的是一个指针数组,它可以这么用:int a,b,c,*p[3]; p[0]=a;p[1]=b;p[2]=c,那么我们p[n]实施++操作的时候,它一样的只是偏移4个字节。而 int (*p)[3],就不同了,它是一个数组指针,每次对它进行++操作时,它正确的偏移了12个字节。好了,现在可以这么使用指针了,int a[2][3],(*p)[3];p=a;p++; 可以从a[0]偏移到a[1]了,但是,要取得a[0][0]的值怎么办呢?前面说过,这个a是数组的数组,意味着a[0] 值是另一个数组的首地址,所以我们可以使用 int 型指针,来把 a[0] 当做一个一维数组来操作了。int *pp;pp=*p(注意,是pp=*p,而不是pp=p ,p的值是这个二维数组a的首地址,*p的值就是a[0]的值,存储的是 包含三个元素的 数组首地址。)那么,pp++,int 型 偏移 4 字节 ,能正常读取了,顺理成章~~~:)那如果int [2][3][4]呢?不说啦,思路延伸一下就行了。
bar3d是Turbo C工具中绘制长方体(也可理解为绘制三维条形图)的一个图形函数。其基本语法如下:
bar3d(int left, int top, int right, int bottom, int depth, int topflag);
其中:int left, int top构成第一个坐标点,即屏幕中长方体前面(即离我们最近的长方形)左上角的一个点;
int right, int bottom构成第二个坐标点,即屏幕中长方体前面(即离我们最近的长方形)右下角的一个点;
由以上两个坐标点就可以确定一个长方形,然后结合int depth(用于确定长方体的厚度,即长方体前后两个面的间距),就可以完全确定长方体的形状。
int topflag 用于对长方体的顶部显示方式。
举例:例如在Turbo C++工具中编写的C程序:
# include graphics.h
# include stdio.h
void main()
{
int graphdriver=DETECT, graphmode;
initgraph(graphdriver,graphmode,"C:\\TURBOC3\\BGI"); //*图形系统初始化*/
bar3d(0,0,250,250,10,1);
getch() ;
closegraph(); // 关闭图形模式//
}
其运行结果为:
运行结果
3D"是three-dimensional的缩写,就是三维图形。在计算机里显示3d图形,就是说在平面里显示三维图形。不像现实世界里,真实的三维空间,有真实的距离空间。计算机里只是看起来很像真实世界,因此在计算机显示的3d图形,就是让人眼看上就像真的一样。人眼有一个特性就是近大远小,就会形成立体感。计算机屏幕是平面二维的,我们之所以能欣赏到真如实物般的三维图像,是因为显示在计算机屏幕上时色彩灰度的不同而使人眼产生视觉上的错觉,而将二维的计算机屏幕感知为三维图像。基于色彩学的有关知识,三维物体边缘的凸出部分一般显高亮度色,而凹下去的部分由于受光线的遮挡而显暗色。这一认识被广泛应用于网页或其他应用中对按钮、3d线条的绘制。比如要绘制的3d文字,即在原始位置显示高亮度颜色,而在左下或右上等位置用低亮度颜色勾勒出其轮廓,这样在视觉上便会产生3d文字的效果。具体实现时,可用完全一样的字体在不同的位置分别绘制两个不同颜色的2d文字,只要使两个文字的坐标合适,就完全可以在视觉上产生出不同效果的3d文字