概述
好吧!在这一章开始之前先说一说我当初的心得吧!
当初,链表,栈和队列,因为老师强调的比较多,运用的也比较多,理解得也很好,代码量也不大,所以完成了比较顺利。再后来,关于串的三种存储表示,代码量稍稍增加,但也不成问题。结果一进入第五章,人就懵了!简直就像之前还在印度平原漫步,结果一抬头,应该是一仰头,就看见喜马拉雅山了!!!着实吓着了,想放弃了,结果还是坚持下去了!
尤其第一节的数组的顺序表示和实现,里面有个很揪心的变参函数!查了很久,大概明白了是什么意思(不过在学术上,最好不要不求甚解!“大概”不好!!)结果也与编译器有若干联系。不过还算让自己满意!
再后来,自己敲的代码也多了,也没觉得当初的代码敲得怎么揪心了,只是有个浅浅的记忆而已!不过我从中也获得了一个很好的启示:当你遇到一个难题时,不要紧,再去找一个更难的题做吧!那样你就会觉得以前那个题也就那么点难度!
#include< stdio.h >
#include< stdlib.h >
#include< stdarg.h > //提供宏va_start,va_arg,va_end.用于存取变长参数表#define MAX_ARRAY_DIM 8 //数组的最大维数
#define TRUE 1
#define FALSE 0
#define OK 1
#define ERROR 0
#define INFEASIBLE -1
#define OVERFLOW -2
#define UNDERFLOW -3
typedef int Status; //函数一般有返回值最好,即使没有用,也可以用来判断
typedef int ElemType ;typedef struct
{
ElemType *base ; //数组元素基址
int dim ; //数组维数
int *bounds ; //数组维界基址
int *constants ; //数组映像函数常量基址
}Array ;//-------基本操作的函数原型说明--------
Status InitArray(Array * A, int dim, ...);
//若维数dim和随后的各维长度合法,则构造相应的数组A,并返回OK
Status SestroyArray(Array * A);
//销毁数组A
Status Value(Array A, ElemType *e ,...);
//A是n维数组,e为元素变量,随后是n个下标值。
//若各下标不超界,则e赋值为所指定的A的元素值,并返回OK
Status Assign(Array * A, ElemType e, ...);
//A是n维数组,e为元素变量,随后是n各下标值
//若各下标不超界,则将e的值赋给所指定的A的元素,并返回OK//--------------------------basic function!----------------------------//
Status InitArray( Array *A , int dim , ... )
{
va_list ap ; //就把 ap 当成是一个 char * 的指针;
int elemtotal , i ;
if( dim < 1 || dim > MAX_ARRAY_DIM )
{
return ERROR ;
}
( *A ).dim = dim ;
( *A ).bounds = ( int * ) malloc ( dim * sizeof( int ) ) ;
if( !( *A ).bounds )
{
exit( OVERFLOW ) ;
}elemtotal = 1 ;
va_start( ap , dim ) ; //ap为va_list类型,用于存放变长参数表信息的数组
//va_start(ap, e); va_start 是一个宏,展开后,实际上相当于 ap = (char*)&e + sizeof(e);for( i = 0 ; i < dim ; ++ i )
{
( *A ).bounds[ i ] = va_arg( ap , int ) ; //T var = va_arg(ap, T); 这个相当于 两句话, T var = *(T*)ap; ap+= sizeof(T);
if( ( *A ).bounds[ i ] < 0 )
{
return UNDERFLOW ;
}
elemtotal *= ( *A ).bounds[ i ] ;
}va_end( ap ) ; //#define va_end(ap) (void)0
( *A ).base = ( ElemType *) malloc ( elemtotal * sizeof( ElemType ) ) ;
if( !( *A ).base )
{
exit( OVERFLOW ) ;
}//求映像函数的常熟Ci,并存入(*A).constants[i-1] , i =1,2……dim;
( *A ).constants = ( int * )malloc( dim * sizeof( int ) ) ;
if( !( *A ).constants )
{
exit( OVERFLOW ) ;
}( *A ).constants[ dim - 1 ] = 1 ; //L= 1 , 指针的增减以元素的大小为单位 ???
for( i = dim - 2 ; i >= 0 ; -- i )
{
( *A ).constants[ i ] = ( *A ).bounds[ i + 1 ] * ( *A ).constants[ i + 1 ] ;
}return OK ;
}
Status DestroyArray( Array *A )
{
if( !( *A ).base )
{
return ERROR ;
}
free( ( *A ).base ) ;
( *A ).base = NULL ;if( !( *A ).bounds )
{
return ERROR ;
}
free( ( *A ).bounds ) ;
( *A ).bounds = NULL ;if( !( *A ).constants )
{
return ERROR ;
}
free( ( *A ).constants ) ;
( *A ).constants = NULL ;
return OK ;
}Status Locate( Array A ,va_list ap , int *off )
{ //若ap指示的各下标值合法,则求出该元素在A中的相对地址off
int i , ind ;
( *off ) = 0 ;for( i = 0 ; i < A.dim ; ++ i )
{
ind = va_arg( ap , int ) ; // //T var = va_arg(ap, T); 这个相当于 两句话, T var = *(T*)ap; ap+= sizeof(T);
if( ind < 0 || ind >= A.bounds[ i ] )
{
return OVERFLOW ;
}
( *off ) += A.constants[ i ] * ind ;
}return OK ;
}
Status Value( Array A , ElemType *e , ... )
{ //A是n维数组,*e为元素变量,随后是n个下标值
//若各下标不超界,则e赋值为所指定的A的元素值,并返回OK
va_list ap ;
int off , result ;va_start( ap , *e ) ;
if( ( result = Locate( A , ap , &off ) ) <= 0 )
{
return result ;
}
*e = *( A.base + off ) ;
return OK ;
}Status Assign( Array *A , ElemType e , ... )
{ // A是n维数组,e为元素变量,随后是n各下标值
//若各下标不超界,则将e的值赋给所指定的A的元素,并返回OK
va_list ap ;
int off , result ;va_start( ap , e ) ;
if( ( result = Locate( *A , ap , &off ) ) <= 0 )
{
return result ;
}
va_end( ap ) ;
*( ( *A ).base + off ) = e ;return OK ;
}//-------------------------------main function!----------------------------//
void main( )
{
Array A ;
ElemType e ;
int i , j ;
int t = 1 ;InitArray( &A , 2 , 2 , 2 ) ;
for( i = 0 ; i < 2 ; ++ i )
{
for( j = 0 ; j < 2 ; ++ j )
{
Assign( &A , t , i , j ) ;
++ t ;
}
}for( i = 0 ; i < 4 ; ++ i )
{
printf( "%-3d" , A.base[ i ] ) ;
}printf( "n" ) ;
Value( A , &e , 0 , 0 ) ;
printf( "%dn" , e ) ;
}
最后
以上就是贪玩秋天为你收集整理的第五章(1)数组的顺序表示和实现的全部内容,希望文章能够帮你解决第五章(1)数组的顺序表示和实现所遇到的程序开发问题。
如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。
发表评论 取消回复