题目:顺序表的基本操作实现
内容
实现顺序表的初始化,
输出顺序表中各元素的值,
在顺序表中插入数据元素,
删除数据元素,
求顺序表的长度,
顺序表的逆置,
顺序表的按值从小到大排序,
合并有序的两个顺序表等操作。
要求
要有能根据用户输入选择不同运算的菜单选择界面。
顺序表中数据元素的类型统一抽象表示为ElemType类型,具体类型不限,可以是整型、实型、字符型、或者是自己构造的一种结构体类型。
分析
本题考查的是对顺序表的基本操作,从顺序表的结构体类型的创建,到各种函数功能的实现。
创建顺序表数据类型
自定义数据类型Elemtype
,在结构体中有两个结构体成员,分别为 Elemtype
类型的Data[MAXSIZE]
,以及顺序表长度Length
,注意这里的Length
并不是数组长度,数组的长度始终是MAXSIZE
,这里表示的是数组中含有元素的个数。
#define MAXSIZE 50
typedef int Elemtype;
typedef struct {
Elemtype Data[MAXSIZE];
int Length;
} SeqList;
初始化顺序表
将顺序的Length
置为0
void Init(SeqList &S) {
for (int i = 0; i < MAXSIZE; ++i)
S.Data[i] = 0;
S.Length = 0;
}
顺序表的插入操作
注意,这里是在第loc
位后插入元素e
,
bool Insert(SeqList &S, int loc, Elemtype e) {
if (loc < 1 || loc > S.Length)//输入数据不合法
return false;
if (S.Length >= MAXSIZE)//顺序表已满,无法插入
return false;
for (int i = S.Length; i >= loc; i--)//这里是i = S.Length而不是i = S.Length-1是因为下面的操作,
//我们要把数据往后移动一位,而S.Length恰好就是下一位的索引
S.Data[i] = S.Data[i - 1];
S.Data[loc] = e;
S.Length++;
return true;
}
顺序表删除操作
bool Delete(SeqList &S, int loc, Elemtype &e) {
if (loc < 1 || loc > S.Length)
return false;
if (S.Length >= MAXSIZE)
return false;
e = S.Data[loc - 1];
for (int i = loc; i < S.Length; i++)
S.Data[i - 1] = S.Data[i];//这里一开始i我写成1了找了半天bug wdnmd
S.Length--;
return true;
}
求顺序表长度
我奶说,这个她都会
int SeqListLength(SeqList &S) {
return S.Length;
}
顺序表的逆置
这里使用了swap()
函数,不懂的同学就手敲一下函数,原生c语言貌似没有,
void Inverse(SeqList &S) {
for (int i = 0; i <= S.Length / 2; ++i)
swap(S.Data[i], S.Data[S.Length - 1 - i]);
/*
Elemtype temp;
temp = S.Data[i];
S.Data[i] = S.Data[S.Length - i];
S.Data[S.Length - i] = temp;
*/
}
顺序表排序
这里我使用的是快速排序,l
指的是需要排序段左边界元素的下标索引,r
指的是需要排序段由边界元素的下标索引,对应此题
l = 0
r = S.Length - 1
,使用快速排序可以很方便的帮我解决问题,有关快速排序的代码解释如下。
除了使用快速排序,还可以使用堆排序,希尔排序,归并排序等等。
void QuickSort(int q[], int l, int r) {
if (l >= r) return;
int i = l - 1, j = r + 1, x = q[(l + r) >> 1];//ij初始位置为边界两边,x取中间 >>是移位运算符,不懂的去查
while (i < j) {//如果i<j 就循环操作,使得x左边的都<x,x右边的都>x,然后分别递归排序两边
do i++; while (q[i] < x);//i向右寻找,遇到>x的停下
do j--; while (q[j] > x);//j向左寻找,遇到<x的停下
if (i < j) swap(q[i], q[j]);//如果满足,找到的数大的在左边,小的在右边,就交换两个数
}
QuickSort(q, l, j), QuickSort(q, j + 1, r);//递归排序左右区间
}
void SeqListSort(SeqList &S) {
QuickSort(S.Data, 0, S.Length - 1);
}
顺序表合并
这里需要申请一个新的顺序表用来存放合并的数组,这里我们可以偷懒一下,我们可以先把两个顺序表依次插入到新的顺序表中,然后调用我们写的排序函数SeqListSort
即可完成顺序表的有序合并
bool Merge(SeqList &S1, SeqList &S2, SeqList &S3) {
if (S1.Length + S2.Length > MAXSIZE)
return false;
S3.Length = S1.Length + S2.Length;
for (int i = 0; i < S3.Length; ++i) {
if (i < S1.Length) {
S3.Data[i] = S1.Data[i];
} else
S3.Data[i] = S2.Data[i - S1.Length];
}
SeqListSort(S3);
return true;
}
顺序表的输出
void Print(SeqList &S) {
for (int i = 0; i < S.Length; ++i)
cout << S.Data[i] << " ";
cout << endl;
}
顺序表的创建
void Create(SeqList &S) {
cout << "Let's start the creation of the SeqList!" << endl;
cout << "Please enter the length of the SeqList:" << endl;
int length;
cin >> length;
S.Length = length;
cout << "Please enter data:" << endl;
Elemtype temp;
for (int i = 0; i < length; ++i) {
cin >> temp;
S.Data[i] = temp;
}
}
完整代码
#include <bits/stdc++.h>
using namespace std;
#define MAXSIZE 50
typedef int Elemtype;
typedef struct {
Elemtype Data[MAXSIZE];
int Length;
} SeqList;
void Init(SeqList &S) {
for (int i = 0; i < MAXSIZE; ++i)
S.Data[i] = 0;
S.Length = 0;
}
void Print(SeqList &S) {
for (int i = 0; i < S.Length; ++i)
cout << S.Data[i] << " ";
cout << endl;
}
bool Insert(SeqList &S, int loc, Elemtype e) {
if (loc < 1 || loc > S.Length)
return false;
if (S.Length >= MAXSIZE)
return false;
for (int i = S.Length; i >= loc; i--)
S.Data[i] = S.Data[i - 1];
S.Data[loc] = e;
S.Length++;
return true;
}
bool Delete(SeqList &S, int loc, Elemtype &e) {
if (loc < 1 || loc > S.Length)
return false;
if (S.Length >= MAXSIZE)
return false;
e = S.Data[loc - 1];
for (int i = loc; i < S.Length; i++)
S.Data[loc - 1] = S.Data[loc];
S.Length--;
return true;
}
int SeqListLength(SeqList &S) {
return S.Length;
}
void Inverse(SeqList &S) {
for (int i = 0; i <= S.Length / 2; ++i)
swap(S.Data[i], S.Data[S.Length - 1 - i]);
}
void QuickSort(int q[], int l, int r) {
if (l >= r) return;
int i = l - 1, j = r + 1, x = q[(l + r) >> 1];
while (i < j) {
do i++; while (q[i] < x);
do j--; while (q[j] > x);
if (i < j) swap(q[i], q[j]);
}
QuickSort(q, l, j), QuickSort(q, j + 1, r);
}
void SeqListSort(SeqList &S) {
QuickSort(S.Data, 0, S.Length - 1);
}
bool Merge(SeqList &S1, SeqList &S2, SeqList &S3) {
if (S1.Length + S2.Length > MAXSIZE)
return false;
S3.Length = S1.Length + S2.Length;
for (int i = 0; i < S3.Length; ++i) {
if (i < S1.Length) {
S3.Data[i] = S1.Data[i];
} else
S3.Data[i] = S2.Data[i - S1.Length];
}
SeqListSort(S3);
return true;
}
void Create(SeqList &S) {
cout << "Let's start the creation of the SeqList!" << endl;
cout << "Please enter the length of the SeqList:" << endl;
int length;
cin >> length;
S.Length = length;
cout << "Please enter data:" << endl;
Elemtype temp;
for (int i = 0; i < length; ++i) {
cin >> temp;
S.Data[i] = temp;
}
}
char Select() {
char ch;
cout << "Please select the SeqList you want to operate on(input A or B):" << endl;
cin >> ch;
return ch;
}
int main() {
SeqList S1, S2, S3;
Init(S1);
Init(S2);
Init(S3);
Create(S1);
Create(S2);
char k;
cout << "SeqList operation codes:\n"
"I = Insert\n"
"D = Delete\n"
"L = Get SeqList Length\n"
"R = Inverse\n"
"S = SeqListSort(Quick Sort)\n"
"M = Merge\n"
"P = Print" << endl;
for (;;) {
cout << "\nPlease enter SeqList operation codes:" << endl;
cin >> k;
switch (k) {
case ('I'): {
char flag = Select();
int location;
Elemtype data;
cout << "Please enter the data position and data you need to insert by a blank space:" << endl;
cin >> location >> data;
switch (flag) {
case ('A'): {
if (Insert(S1, location, data))
cout << "Insert succeed" << endl;
else
cout << "Insert failed" << endl;
break;
}
case ('B'): {
if (Insert(S2, location, data))
cout << "Insert succeed" << endl;
else
cout << "Insert failed" << endl;
break;
}
default:
cout << "Enter the ERROR codes" << endl;
break;
}
break;
}
case ('D'): {
char flag = Select();
int location;
Elemtype data;
cout << "Please enter the data position you want to Delete:" << endl;
cin >> location;
switch (flag) {
case ('A'): {
if (Delete(S1, location, data))
cout << "Delete succeed" << endl;
else
cout << "Delete failed" << endl;
break;
}
case ('B'): {
if (Delete(S2, location, data))
cout << "Delete " << data << " succeed" << endl;
else
cout << "Delete " << data << " failed" << endl;
break;
}
default:
cout << "Enter the ERROR codes." << endl;
break;
}
break;
}
case ('L'): {
switch (Select()) {
case ('A'): {
cout << "The SeqList Length is:" << SeqListLength(S1) << endl;
break;
}
case ('B'): {
cout << "The SeqList Length is:" << SeqListLength(S2)<< endl;
break;
}
default:
cout << "Enter the ERROR codes." << endl;
break;
}
break;
}
case ('R'): {
switch (Select()) {
case ('A'): {
Inverse(S1);
cout << "Inverse Succeed" << endl;
break;
}
case ('B'): {
Inverse(S2);
cout << "Inverse Succeed" << endl;
break;
}
default:
cout << "Enter the ERROR codes." << endl;
break;
}
break;
}
case ('S'): {
switch (Select()) {
case ('A'): {
SeqListSort(S1);
cout << "QuickSort Succeed" << endl;
break;
}
case ('B'): {
SeqListSort(S2);
cout << "QuickSort Succeed" << endl;
break;
}
default:
cout << "Enter the ERROR codes." << endl;
break;
}
break;
}
case ('P') : {
switch (Select()) {
case ('A'): {
Print(S1);
cout << "Print Succeed" << endl;
break;
}
case ('B'): {
Print(S2);
cout << "Print Succeed" << endl;
break;
}
default:
cout << "Enter the ERROR codes." << endl;
break;
}
break;
}
case ('M') : {
Merge(S1, S2, S3);
cout << "Merge Succeed" << endl;
Print(S3);
break;
}
default:
return 0;
}
}
}
本文为作者原创,仅供学习使用。如有错误可联系作者。