(1) Objetivo do experimento Através deste experimento, você pode entender profundamente os conceitos da estrutura lógica e estrutura física da tabela de sequência, dominar a realização de programação das operações básicas da tabela de sequência, prestar atenção ao movimento dos elementos de dados durante as operações de inserção da tabela de sequência , exclusão, etc., e treine os alunos a considerar ao escrever programas. A robustez do programa, considere o problema de forma abrangente e domine o método de retornar o resultado da função por meio do parâmetro da função. (2) Conteúdo experimental Programa para realizar a operação básica da tabela linear definida no Capítulo 2 do livro sob a tabela de sequência, e realizar a fusão de duas tabelas lineares ordenadas não decrescentes de acordo com as operações básicas já realizadas. Observe que ao mesclar, se houver elementos repetidos ( elementos repetidos dentro de uma tabela e entre duas tabelas), mantenha um. (3) Requisitos experimentais (a) Encontrar o predecessor refere-se a inserir um valor de elemento (em vez de uma posição) para encontrar o valor do elemento predecessor imediato do elemento na tabela de sequência. Encontrar o sucessor significa: inserir um valor de elemento (em vez de uma posição) e encontrar o valor do elemento sucessor imediato do elemento na tabela de sequência; (b) Para modificar o tipo do elemento de dados convenientemente, use redefinição de tipo, que pode facilmente modificar a tabela linear O tipo do elemento de dados em; (c) O resultado de retorno da maioria das funções deve ser um status de se a execução da função foi bem-sucedida e o valor do resultado específico será retornado somente se o a execução for bem-sucedida; (d) Ao testar cada função, é necessário testar também a situação ilegal. Para obter detalhes, consulte os seguintes casos de teste: (e) Use o formulário de menu para corresponder a cada operação, para que possa ser compilado em um pequeno software completo. A interface de referência é a seguinte. Nota: Durante a execução do programa, o menu não deve ser feito para atualizar a tela e os dados testados não devem ser apagados, para que seja conveniente para capturas de tela e visualização. Nota: A destruição refere-se a free(L.elem); L.elem=NULL; L.length=0; L.listsize=0; return TRUE. Vazio significa: L.length=0 ;return TRUE. (3) Aceite/casos de teste Chame cada operação através do menu, pontos de teste:
- Se o programa pode ser controlado sem executar outras operações antes da inicialização, ou seja, se a tabela linear não for inicializada, outras funções não poderão ser executadas normalmente. Se você optar por executar outras operações, deverá ser solicitado a inicializar primeiro;
- Primeiro, selecione o menu 1 para inicializar uma tabela de sequência (inicializar a tabela de sequência refere-se a inicializar uma tabela linear vazia, o número de elementos nela é 0);
- Selecione o menu 10, insira dados (posição, dados), para testar a posição de inserção ilegal (0,1), (2,1) e insira 3 dados (1, 20), (1, 10), ( 3,30 );
- Exibir os dados na tabela de sequência, a saída da tela 10, 20, 30;
- Vazio, a lista de sequência de saída da tela não está vazia;
- Comprimento da tabela de sequência de saída, saída de tela 3;
- Para obter o elemento na posição especificada, é necessário medir a situação em que a posição especificada está fora do intervalo de [1, 3] e a situação dentro;
- Posicionamento, entrada: 40, saída: não existe, entrada 20, posição de saída é 2;
- Para encontrar o predecessor direto, você precisa medir o predecessor do primeiro elemento, o predecessor direto do elemento que não existe na tabela de sequência e o predecessor direto de outros elementos; entrada 10, saída: o primeiro elemento não tem predecessor, entrada 20, saída do predecessor é 10 , entrada 40, saída de que o elemento não existe;
- Para encontrar o sucessor direto, você precisa medir o sucessor do último elemento, o sucessor direto do elemento que não existe na tabela de sequência e o sucessor direto de outros elementos; o mesmo que acima para encontrar o predecessor;
- Excluir, para medir a situação em que a posição está fora do intervalo de [1, 3] e a situação dentro;
- Depois de limpar a operação, meça o comprimento para determinar se está vazio; depois de limpar, teste as funções dos menus 6 a 11 para ver se eles podem ser solicitados corretamente.
- Destrua a tabela de sequência, se você pode executar operações como inserção e exclusão após destruir a tabela linear, se escolher outras operações, será informado que a tabela linear foi destruída e não existe;
- Teste a operação de mesclagem. Os elementos na primeira tabela linear são (2,3,3,4,5) e os conteúdos na segunda tabela linear são (1,4,5,6,6,7). mesclar O resultado, por favor saída.
#include<iostream>
using namespace std;
#define ok 1
#define false 0
#define overflow -2
#define maxsize 200
typedef int Status;
typedef int ElemType;
typedef struct{
ElemType *elem;
int length;
int listsize;
}SqList;
Status InitList(SqList &L);
Status DestoryList(SqList &L);
Status ClearList(SqList &L);
Status ListLength(SqList L);
Status ListEmpty(SqList L);
Status GetElemt(SqList L,int i);
Status LocateElemt(SqList L,int cur_e);
Status PriorElemt(SqList L,int i,int *pri_e);
Status NextElemt(SqList L,int i,int *next_e);
Status InsertElemt(SqList &L,int i,int e);
Status DeleteElem(SqList& L, int i);
Status ListTraver(SqList& L);
void MergeList(SqList LA, SqList LB, SqList& LC);
int main()
{
int i, j, m, n, inser, dizhi, cur_e, pri_e, next_e;
SqList L;
SqList LA;
SqList LB;
SqList LC;
L.elem = NULL;
cout << "1.初始化线性表" << endl;
cout << "2.销毁线性表" << endl;
cout << "3.清空线性表" << endl;
cout << "4.判断线性表是否为空" << endl;
cout << "5.求线性表长度" << endl;
cout << "6.获取线性表中指定位置的元素" << endl;
cout << "7.获取线性表元素的位置" << endl;
cout << "8.求前驱" << endl;
cout << "9.求后驱" << endl;
cout << "10.在线性表指定位置插入元素" << endl;
cout << "11.删除线性表指定位置的元素" << endl;
cout << "12.显示线性表" << endl;
cout << "13.合并两个非递减有序的线性表" << endl;
cout << "\t退出,输入一个负数!" << endl;
do {
cout << "请输入你的选择:" << endl;
cin >> n;
cout << endl;
switch (n)
{
case 1:InitList(L);
break;
case 2:DestoryList(L);
break;
case 3:ClearList(L);
break;
case 4:ListEmpty(L);
break;
case 5:ListLength(L);
break;
case 6:cout << "输入指定位置" <<endl;
cin >> i;
GetElemt(L, i);
break;
case 7:
cout << "获取线性表元素的位置:" << endl;
cin >> cur_e;
LocateElemt(L, cur_e);
break;
case 8:
cout << "输入元素,求它的前驱:" << endl;
cin >> cur_e;
PriorElemt(L, cur_e, &pri_e);
break;
case 9:
cout << "输入元素,求它的后驱:" << endl;
cin >> cur_e;
NextElemt(L, cur_e, &next_e);
break;
case 10:
cout << "输入指定位置:" << endl;
cin >> i;
cout << "输入要插入的元素:" << endl;
cin >> inser;
InsertElemt(L, i, inser);
break;
case 11:
cout << "输入要删除元素的位置:" << endl;
cin >> i;
DeleteElem(L, i);
break;
case 12:
ListTraver(L);
break;
case 13:
/*int num1, num2;
LA.elem = (ElemType*)malloc(maxsize * sizeof(ElemType));
if (!LA.elem) exit(overflow);
LA.length = 0;
LA.listsize = maxsize;
cout << "请输入你要输入LA的个数" << endl;
cin >> num1;
cout << "请输入数据" << endl;
for (i = 0; i < num1; i++)
{
cin >> LA.elem[i];
LA.length++;
}
int num3, num4;
LB.elem = (ElemType*)malloc(maxsize * sizeof(ElemType));
if (!LB.elem) exit(overflow);
LB.length = 0;
LB.listsize = maxsize;
cout << "请输入你要输入LB的个数" << endl;
cin >> num3;
cout << "请输入数据" << endl;
for (i = 0; i < num3; i++)
{
cin >> LB.elem[i];
LB.length++;
}*/
InitList(LA);
InitList(LB);
LC.elem = (ElemType*)malloc(maxsize * sizeof(ElemType));
if (!LC.elem) exit(overflow);
LC.length = 0;
LC.listsize = maxsize;
MergeList(LA, LB, LC);
break;
default:
cout << "请输入1~13内的数字!" << endl;
break;
}
} while (n > 0);
}
Status InitList(SqList &L)
{
int num, i;
L.elem=(ElemType *)malloc(maxsize*sizeof(ElemType));
if(!L.elem) exit(overflow);
L.length=0;
L.listsize=maxsize;
cout<<"线性表初始化成功!"<<endl;
cout << "请输入你要输入的个数" << endl;
cin >> num;
cout << "请输入数据" << endl;
for (i = 0; i < num; i++)
{
cin >> L.elem[i];
L.length++;
}
return ok;
}
Status DestoryList(SqList &L){
if(L.elem==NULL)
{cout<<"请先初始化线性表"<<endl;
return false;
}
free(L.elem);
L.elem=NULL;
L.length = 0;
L.listsize = 0;
cout<<"线性表销毁成功"<<endl;
}
Status ClearList(SqList& L) {
if (L.elem == NULL)
{
cout << "请先初始化线性表!" << endl;
return false;
}
L.length = 0;
cout << "线性表清除成功" << endl;
}
Status ListEmpty(SqList L) {
if (L.length == 0)
{
cout << "线性表为空" << endl;
return ok;
}
else
{
cout << "该线性表不为空!" << endl;
return false;
}
}
Status ListLength(SqList L) {
if (L.elem == NULL)
{
cout << "请先初始化线性表" << endl;
return false;
}
cout << "线性表长度为:" << L.length << endl;
return ok;
}
Status GetElemt(SqList L, int i) {
if (L.elem == NULL)
{
cout << "请先初始化线性表" << endl;
return false;
}
if (i < 1 || i > L.length)
{
cout << "不存在,请输入线性表长度范围内的数" << endl;
return false;
}
cout << "该元素为:" << L.elem[i - 1] << endl;
return ok;
}
Status LocateElemt(SqList L, int cur_e) {
if (L.elem == NULL)
{
cout << "请先初始化线性表" << endl;
return false;
}
int i = 0;
int m = 0;
for (i = 0; i < L.length; i++)
{
if (L.elem[i] == cur_e)
{
cout << "该元素的位置为" << i + 1 << endl;
m = -1;
return ok;
}
}
if (m == 0)
{
cout << "该元素不在线性表中" << endl;
return false;
}
}
Status PriorElemt(SqList L, int cur_e, int* pri_e) {
int i = 0;
if (L.elem == NULL)
{
cout << "请先初始化线性表" << endl;
return false;
}
while ((L.elem[i] != cur_e) && (i < L.length))
{
i++;
}
if (i < L.length)
{
if (i == 0)
{
cout << "该元素位于元首,没有前驱!" << endl;
return false;
}
*pri_e = L.elem[i - 1];
cout << "该元素的前驱:" << *pri_e << endl;
return ok;
}
else
{
cout << "该线性表中没有该元素!" << endl;
return ok;
}
}
Status NextElemt(SqList L, int cur_e, int* next_e) {
if (L.elem == NULL)
{
cout << "请先初始化线性表" << endl;
return false;
}
int i = 0;
while ((L.elem[i] != cur_e) && (i < L.length))
{
i++;
}
if (i < L.length)
{
if (i == L.length - 1)
{
cout << "该元素没有后继!" << endl;
return false;
}
*next_e = L.elem[i + 1];
cout << "该元素的后继:" << *next_e << endl;
return ok;
}
else
{
cout << "该线性表中没有该元素!" << endl;
return false;
}
}
Status InsertElemt(SqList & L, int i, int e) {
int j;
if (L.elem == NULL)
{
cout << "请先初始化线性表" << endl;
return false;
}
if (i < 1 || i > L.length + 1)
{
cout << "请输入线性表长度以内的数" << endl;
return false;
}
if (L.length == maxsize)
{
return false;
}
for (j = L.length; j >= i - 1; j--)
{
L.elem[j + 1] = L.elem[j];
}
L.elem[i - 1] = e;
L.length++;
cout << "元素插入成功" << endl;
return ok;
}
Status DeleteElem(SqList& L, int i) {
int j;
if (L.elem == NULL)
{
cout << "请先初始化线性表" << endl;
return false;
}
if (i < 1 || i > L.length + 1)
{
cout << "请输入线性表长度以内的数" << endl;
return false;
}
for (j = i - 1; j <= L.length; j++)
{
L.elem[j] = L.elem[j + 1];
}
L.length--;
cout << "删除元素成功!" << endl;
return ok;
}
Status ListTraver(SqList& L) {
int i;
if (L.elem == NULL)
{
cout << "请先初始化线性表" << endl;
return false;
}
cout << "输出该线性表:" << endl;
for (i = 0; i < L.length; i++)
{
cout << L.elem[i] << " ";
}
cout << endl;
return ok;
}
void MergeList(SqList LA, SqList LB, SqList& LC) {
int i, j;
cout << "输出线性表LA:" << endl;
ListTraver(LA);
cout << "输出线性表LB:" << endl;
ListTraver(LB);
int* pa, * pb, * pc, * pa_last, * pb_last;
pa = LA.elem;
pb = LB.elem;
LC.length = LA.length + LB.length;
pc = LC.elem;
pa_last = LA.elem + LA.length - 1;
pb_last = LB.elem + LB.length - 1;
while ((pa <= pa_last) && (pb <= pb_last)) {
if (*pa < *pb)
{
*pc = *pa;
*pc++;
*pa++;
}
else
{
*pc = *pb;
*pc++;
*pb++;
}
}
while (pa <= pa_last)
{
*pc = *pa;
*pc++;
*pa++;
}
while (pb <= pb_last)
{
*pc = *pb;
*pc++;
*pb++;
}
for (int i = 0; i <= LC.length - 1; i++)//查重,去重复值。
{
if (LC.elem[i] == LC.elem[i + 1])
{
for (int j = i + 1; j <= LC.length - 1; j++)
{
LC.elem[j] = LC.elem[j + 1];
}
LC.length--;
}
}
cout << "输出此时的数组LC:" << endl;
ListTraver(LC);
}
|