数据结构实验线性表顺序表

顺序表//附有详细注释
完整代码在最后。

//常量,用于表示函数返回的状态等
#define OVERFLOW -2
#define OK 1
#define ERROR 0

//数据类型说明
typedef int ElemType; //为int类型创建两个新的名字:元素类型和状态
typedef int Status;
#define List_init_size 100 //储存空间最大值
#define Listincrement 10 //线性表存储空间初始分配量

typedef struct {
ElemType *elem; //存储空间基址
int length; //当前长度
int listsize; //当前分配的存储容量
// (以sizeof(ElemType)为单位)
}sqlist;
```
初始化 线性表
```cpp
//初始化线性表:
Status lnitList(sqlist &L) //Status即int类型,用以表示函数返回一种状态:OK 或者 ERROR 或者OVERFLOW
{
//构造一个空线性表L
L.elem=(ElemType *) malloc (List_init_size* sizeof (ElemType)); //ElemType,int的别名
// malloc 函数的功能是为一个对象在堆中分配一个sizeof (ElemType)大小的内存空间,并且返回一个指向这块内存的指针
if (!L.elem) exit (OVERFLOW);
L.length=0;
L.listsize= List_init_size; //储存容量为100
return OK;
}
```
构建线性表的基本操作
```cpp
//在一个线性表中输入N个数据:
Status sqlistinput(sqlist &L, int n)
{
if (n>L.listsize) return ERROR;
for (int i=0; i<n; i++) scanf("%d", &L.elem[i]);
L.length=n;
return OK;
}

//判线性表是否为空
Status ListEmpty(sqlist L)
{
if (!L.length) return ERROR;
else return OK;
}

//求线性表的长度
Status ListLength(sqlist L)
{
return L.length;
}

//将线性表L的数据输出:
Status sqlistoutput(sqlist L)
{
for (int i=0; i<ListLength(L); i++) printf ("%d ", L.elem[i]);
printf ("\n");
return OK;
}
//取线性表的第i个元素,将结果保存在e中
Status GetElem(sqlist l, int i, ElemType &e)
{
if (i<1 || i>l.length+1)
return ERROR;
e=l.elem[i-1]; //数组元素下表从0开始,第i个元素在数组中的下标为i-1
return OK;
}
```
顺序表实验中拓展的线性表操作
```cpp
//两个数据元素是否相等的比较函数
Status equal(ElemType e1, ElemType e2)
{
if (e1==e2)
return OK;
else
return ERROR;
}

//根据compare函数在线性表中定位元素e的位置
int LocateElem_sq(sqlist L, ElemType e, Status (*compare)(ElemType,ElemType)) //成功返回位序,否则返回0
{
int i=1;
ElemType *p; //定义指针用以遍历线性表
p=L.elem; //线性表储存空间基址
while (i<=L.length && !(*compare) (*p++, e)) ++i; //找到e或者遍历完线性表停止循环,i记录位置
if (i<=L.length)
return i;
else
return 0;
}
```
在线性表中求某个元素的前一个元素和后一个元素
```cpp
//在线性表中求某元素的前趋结点,如存在则返回其前趋结点pre_e的值,否则返回出错信息
Status PriorElem(sqlist L, ElemType cur_e, ElemType &pre_e)
{
int pos;
pos=LocateElem_sq(L, cur_e, equal); //pos表示某元素的位置
if (pos==0)
return ERROR;
else if (pos==1)
return OVERFLOW; //overflow 表示位于第一个
else
{
GetElem(L,pos-1,pre_e); //pos-1表示前驱结点的位置
return OK;
}
}

//在线性表中求某元素的后继结点
Status NextElem(sqlist L, ElemType cur_e, ElemType &next_e)
{
int pos;
pos=LocateElem_sq(L, cur_e, equal);
if (pos==0)
return ERROR;
else if (pos==L.length)
return OVERFLOW; //overflow 表示最后一个
else
{
GetElem(L,pos+1,next_e);
return OK;
}
}
```
线性表的插入和删除操作
```cpp
//在线性表中插入一个元素
Status Listinsert_sq(sqlist &L, int i, ElemType e)
{
ElemType *p,*q,*newbase;
if (i<1 || i>L.length+1)
return ERROR;
if (L.length>=L.listsize)
{
newbase=(ElemType *) realloc (L.elem, (L.listsize+Listincrement) * sizeof (ElemType));
//realloc更改已经配置的内存空间,即更改由malloc()函数分配的内存空间的大小。
if (!newbase) exit (OVERFLOW);
L.elem=newbase;
L.listsize+=Listincrement;
}
q=&(L.elem[i-1]); //此时的&为取地址运算符,当前指针q指向线性表的第i个元素
for (p=&(L.elem[L.length-1]); p>=q; --p) //p指向最后一个元素
{
*(p+1)=*p; //此时*为取值运算符,元素后移一位
}
*q=e; //将e赋值给第i个元素
++L.length; //插入一个元素后线性表长度加一
return OK;
}

//在线性表中删除第i个元素,其结果保留在e中
Status Listdelete_sq(sqlist &l, int i, ElemType &e) //删除和插入原理基本相同
{
ElemType *p,*q;
if (i<1 || i>l.length)
return ERROR;
p=&(l.elem[i-1]);
e=*p;
q=&(l.elem[l.length-1]);
for (++p; p<=q; ++p)
{
*(p-1)=*p;
}
--l.length;
return OK;
}
```
主函数
```cpp
int main()
{
sqlist la; //生成对象即线性表la
int m,n,i,e,k,cur_e,pre_e,next_e;

//建立线性表,并输入线性表的数据
lnitList(la);
printf ("请输入线性表 la 的元素个数 n \n");
scanf ("%d", &n);
if(n>0 && n<=List_init_size)
{
printf ("请输入线性表 la 的 n 个元素\n");
sqlistinput(la,n);
sqlistoutput(la);
printf ("\n");
}
else
{
printf ("建立线性表失败,线性表长度最大为%d \n",List_init_size);
return 0;
}
system("pause");
system("cls");

//调用插入函数,对线性表进行插入操作
printf ("当前线性表为:\n");
sqlistoutput(la);
printf ("请输入插入的元素的位置和插入的值 \n");
scanf ("%d%d", &i, &e); //i代表位置,e代表数值
m=Listinsert_sq(la, i, e);
if(m!=1) printf ("插入失败\n");
else sqlistoutput(la);
system("pause");
system("cls");

//调用删除函数,对线性表进除删操作
printf ("当前线性表为:\n");
sqlistoutput(la);
printf ("请输入要删除的元素的位置\n");
scanf ("%d", &i);
m=Listdelete_sq(la, i, e);
if(m!=1) printf ("删除失败\n");
else
{
printf ("删除的数据是%d \n", e);
sqlistoutput(la);
}
system("pause");
system("cls");

//调用GetElem()函数,取第i个位置的元素的值。
printf ("当前线性表为:\n");
sqlistoutput(la);
printf ("请输入要获得哪个位置的元素\n");
scanf ("%d", &i);
m=GetElem(la, i, e);
if(m!=1) printf ("查找失败\n");
else printf ("线性表中第 %d 位查找到的数据是 %d \n", i, e);
system("pause");
system("cls");

//调用LocateElem_sq函数,求元素cur_e的位置。
printf ("当前线性表为:\n");
sqlistoutput(la);
printf ("请输入要获得哪个元素的位置\n");
scanf ("%d", &cur_e);
k=LocateElem_sq(la, cur_e, equal);
if(k==0) printf ("查找失败\n");
else printf (" %d 在线性表中的位置是 %d \n", cur_e, k);
system("pause");
system("cls");

//调用PriorElemQ函数 求元素cur_e的前驱。
printf ("当前线性表为:\n");
sqlistoutput(la);
printf ("求元素的前驱,请输入数据\n");
scanf ("%d", &cur_e);
m=PriorElem(la, cur_e, pre_e);
if(m!=1) printf ("查找失败\n");
else printf (" %d 元素的前驱是 %d \n", cur_e, pre_e);
system("pause");
system("cls");

//调用NextElem()函数,求元素cur_e的后继。
printf ("当前线性表为:\n");
sqlistoutput(la);
printf ("求元素的后继,请输入数据\n");
scanf ("%d", &cur_e);
m=NextElem(la, cur_e, next_e);
if(m!=1) printf ("查找失败\n");
else printf (" %d 元素的后继是 %d \n",cur_e, next_e);
return 0;
}
```
最后,如果觉得这篇博客能帮助到你,请点赞、关注、收藏,后续我会持续更新,谢谢。

  1 #define OVERFLOW -2
  2 #define OK 1
  3 #define ERROR 0
  4 
  5 //数据类型说明
  6 typedef int ElemType;           //为int类型创建两个新的名字:元素类型和状态
  7 typedef int Status;
  8 #define List_init_size 100      //储存空间最大值
  9 #define Listincrement 10       //线性表存储空间初始分配量
 10 
 11 typedef struct {
 12     ElemType *elem;          //存储空间基址
 13     int length;              //当前长度
 14     int listsize;            //当前分配的存储容量
 15                              // (以sizeof(ElemType)为单位)
 16 }sqlist;                     //直接定义结构体变量sqlist
 17 
 18 //初始化线性表:
 19 Status lnitList(sqlist &L)        //Status即int类型,用以表示函数返回一种状态:OK 或者 ERROR 或者OVERFLOW
 20 {
 21     //构造一个空线性表L
 22     L.elem=(ElemType *) malloc (List_init_size* sizeof (ElemType)); //ElemType,int的别名
 23     // malloc 函数的功能是为一个对象在堆中分配一个sizeof (ElemType)大小的内存空间,并且返回一个指向这块内存的指针
 24     if (!L.elem) exit (OVERFLOW);
 25     L.length=0;
 26     L.listsize= List_init_size;   //储存容量为100
 27     return OK;
 28 }
 29 
 30 //在一个线性表中输入N个数据:
 31 Status sqlistinput(sqlist &L, int n)
 32 {
 33     if (n>L.listsize) return ERROR;        
 34     for (int i=0; i<n; i++)  scanf("%d", &L.elem[i]);
 35     L.length=n;
 36     return OK;
 37 }
 38 
 39 //判线性表是否为空
 40 Status ListEmpty(sqlist L)
 41 {
 42     if (!L.length) return ERROR;
 43     else return OK;
 44 }
 45 
 46 //求线性表的长度
 47 Status ListLength(sqlist L)
 48 {
 49     return L.length;
 50 }
 51 
 52 //将线性表L的数据输出:
 53 Status sqlistoutput(sqlist L)
 54 {
 55     for (int i=0; i<ListLength(L); i++) printf ("%d  ", L.elem[i]);
 56     printf ("\n");
 57     return OK;
 58 }
 59 
 60 //取线性表的第i个元素,将结果保存在e中
 61 Status GetElem(sqlist l, int i, ElemType &e)
 62 {
 63     if (i<1 || i>l.length+1) 
 64         return ERROR;
 65     e=l.elem[i-1];    //数组元素下表从0开始,第i个元素在数组中的下标为i-1
 66     return OK;
 67 }
 68 
 69 //两个数据元素是否相等的比较函数
 70 Status equal(ElemType e1, ElemType e2)
 71 {
 72     if (e1==e2)
 73         return OK;
 74     else
 75         return ERROR;
 76 }
 77 
 78 //根据compare函数在线性表中定位元素e的位置
 79 int LocateElem_sq(sqlist L, ElemType e, Status (*compare)(ElemType,ElemType))    //成功返回位序,否则返回0
 80 {
 81     int i=1;
 82     ElemType *p;      //定义指针用以遍历线性表
 83     p=L.elem;         //线性表储存空间基址
 84     while (i<=L.length && !(*compare) (*p++, e))     ++i;      //找到e或者遍历完线性表停止循环,i记录位置
 85     if (i<=L.length) 
 86         return i;
 87     else 
 88         return 0;
 89 }
 90 
 91 //在线性表中求某元素的前趋结点,如存在则返回其前趋结点pre_e的值,否则返回出错信息
 92 Status PriorElem(sqlist L, ElemType cur_e, ElemType &pre_e)
 93 {
 94     int pos;
 95     pos=LocateElem_sq(L, cur_e, equal);    //pos表示某元素的位置
 96     if (pos==0) 
 97         return ERROR;
 98     else if (pos==1) 
 99         return OVERFLOW; //overflow 表示位于第一个
100     else 
101     {
102         GetElem(L,pos-1,pre_e);      //pos-1表示前驱结点的位置
103         return OK;
104     }
105 }
106 
107 //在线性表中求某元素的后继结点
108 Status NextElem(sqlist L, ElemType cur_e, ElemType &next_e)
109 {
110     int pos;
111     pos=LocateElem_sq(L, cur_e, equal);
112     if (pos==0) 
113         return ERROR;
114     else if (pos==L.length)
115         return OVERFLOW;     //overflow 表示最后一个
116     else 
117     {
118         GetElem(L,pos+1,next_e);
119         return OK;
120     }
121 }
122 
123 //在线性表中插入一个元素
124 Status Listinsert_sq(sqlist &L, int i, ElemType e)
125 {
126     ElemType *p,*q,*newbase;
127     if (i<1 || i>L.length+1) 
128         return ERROR;
129     if (L.length>=L.listsize) 
130     {
131         newbase=(ElemType *) realloc (L.elem, (L.listsize+Listincrement) * sizeof (ElemType)); 
132         //realloc更改已经配置的内存空间,即更改由malloc()函数分配的内存空间的大小。
133         if (!newbase) exit (OVERFLOW);
134         L.elem=newbase;
135         L.listsize+=Listincrement;
136     } 
137     q=&(L.elem[i-1]);    //此时的&为取地址运算符,当前指针q指向线性表的第i个元素
138     for (p=&(L.elem[L.length-1]); p>=q; --p)    //p指向最后一个元素
139     {
140         *(p+1)=*p;          //此时*为取值运算符,元素后移一位
141     }
142     *q=e;          //将e赋值给第i个元素
143     ++L.length;    //插入一个元素后线性表长度加一
144     return OK;
145 }
146 
147 //在线性表中删除第i个元素,其结果保留在e中
148 Status Listdelete_sq(sqlist &l, int i, ElemType &e)   //删除和插入原理基本相同
149 {
150     ElemType *p,*q;
151     if (i<1 || i>l.length) 
152         return ERROR;
153     p=&(l.elem[i-1]);
154     e=*p;
155     q=&(l.elem[l.length-1]);
156     for (++p; p<=q; ++p) 
157     {
158         *(p-1)=*p;
159     }
160     --l.length;
161     return OK;
162 }
163 
164 int main()
165 {
166     sqlist la;     //生成对象即线性表la
167     int m,n,i,e,k,cur_e,pre_e,next_e;
168 
169 //建立线性表,并输入线性表的数据
170     lnitList(la);
171     printf ("请输入线性表 la 的元素个数 n \n");
172     scanf ("%d", &n);
173     if(n>0 && n<=List_init_size)
174     {
175         printf ("请输入线性表 la 的 n 个元素\n"); 
176         sqlistinput(la,n);
177         sqlistoutput(la);
178         printf ("\n");
179     }
180     else
181     {
182         printf ("建立线性表失败,线性表长度最大为%d \n",List_init_size);
183         return 0;
184     }
185     system("pause");
186     system("cls");
187 
188 //调用插入函数,对线性表进行插入操作
189     printf ("当前线性表为:\n");
190     sqlistoutput(la);
191     printf ("请输入插入的元素的位置和插入的值 \n");
192     scanf ("%d%d", &i, &e);    //i代表位置,e代表数值
193     m=Listinsert_sq(la, i, e);
194     if(m!=1) printf ("插入失败\n");
195     else sqlistoutput(la);
196     system("pause");
197     system("cls");
198 
199 //调用删除函数,对线性表进除删操作
200     printf ("当前线性表为:\n");
201     sqlistoutput(la);
202     printf ("请输入要删除的元素的位置\n");
203     scanf ("%d", &i);
204     m=Listdelete_sq(la, i, e);
205     if(m!=1) printf ("删除失败\n");
206     else
207     {
208         printf ("删除的数据是%d \n", e);
209         sqlistoutput(la);
210     }
211     system("pause");
212     system("cls");
213 
214 //调用GetElem()函数,取第i个位置的元素的值。
215     printf ("当前线性表为:\n");
216     sqlistoutput(la);
217     printf ("请输入要获得哪个位置的元素\n");
218     scanf ("%d", &i);
219     m=GetElem(la, i, e);
220     if(m!=1) printf ("查找失败\n");
221     else printf ("线性表中第 %d 位查找到的数据是 %d \n", i, e);
222     system("pause");
223     system("cls");
224 
225 //调用LocateElem_sq函数,求元素cur_e的位置。
226     printf ("当前线性表为:\n");
227     sqlistoutput(la);
228     printf ("请输入要获得哪个元素的位置\n");
229     scanf ("%d", &cur_e);
230     k=LocateElem_sq(la, cur_e, equal);
231     if(k==0) printf ("查找失败\n");
232     else printf (" %d 在线性表中的位置是 %d \n", cur_e, k);
233     system("pause");
234     system("cls");
235 
236 //调用PriorElemQ函数 求元素cur_e的前驱。
237     printf ("当前线性表为:\n");
238     sqlistoutput(la);
239     printf ("求元素的前驱,请输入数据\n");
240     scanf ("%d", &cur_e);
241     m=PriorElem(la, cur_e, pre_e);
242     if(m!=1) printf ("查找失败\n");
243     else printf (" %d 元素的前驱是 %d \n", cur_e, pre_e);
244     system("pause");
245     system("cls");
246 
247 //调用NextElem()函数,求元素cur_e的后继。
248     printf ("当前线性表为:\n");
249     sqlistoutput(la);
250     printf ("求元素的后继,请输入数据\n");
251     scanf ("%d", &cur_e);
252     m=NextElem(la, cur_e, next_e);
253     if(m!=1) printf ("查找失败\n");
254     else printf (" %d 元素的后继是 %d \n",cur_e, next_e);
255     return 0;
256 }

 

posted @ 2021-04-26 21:04  “翎羽”  阅读(208)  评论(0)    收藏  举报