大话数据结构 C++版

前提代码

#include <iostream>
using namespace std;

const int MAXSIZE = 20
typedef struct
{
    int data[MAXSIZE];
    int length;
}SqList;

打印整数

bool visit(int c) //ElemType c表示这个函数接收一个类型为ElemType的参数c,Status表示这个函数返回一个Status类型的值。
{
    cout << c;
    return true;
}

初始化顺序线性表

bool InitList(SqList *L)
{
    L->length = 0;
    return true;
}

int main() 
{
    SqList myList;
    bool initStatus = InitList(&myList);
//调用InitList函数,并将myList的地址作为参数传递给函数。初始化的结果存储在initStatus变量中。
//initStatus变量用于存储InitList函数的返回值,以便在main函数中检查初始化的状态
    if (initStatus == true) 
    {
        cout<<"List initialized successfully.\n";
    } 
    else 
    {
        cout<<"Failed to initialize the list.\n";
    }
    return 0;
}
//在这段代码中,myList和L都是SqList类型的变量,但它们在不同的上下文中使用。

//1. myList是在主函数中声明的变量,用于表示一个具体的顺序表对象。它是主函数的局部变量,
//用于存储顺序表的数据。

//2. L是InitList函数的参数,它是一个SqList类型的指针。在函数调用时,将myList的地址传递给L,
//这样函数可以通过指针修改myList所指向的顺序表对象的属性。在InitList函数内部,使用L->length
//来访问顺序表的长度属性,并将其设置为0,实现了初始化操作。

//总结起来,myList是主函数中的顺序表对象,而L是InitList函数中用于接收顺序表对象地址的参数。
//通过将myList的地址传递给L,函数可以对myList进行初始化操作。

`Status initStatus = InitList(&myList);` 这行代码做了两件事:

1. 调用了 `InitList` 函数,并将 `myList` 的地址(通过 `&` 符号获取)作为参数传递。这是因为 `InitList` 函数需要一个指向 `SqList` 结构体的指针作为参数,所以我们需要传递 `myList` 的地址。

2. 将 `InitList` 函数的返回值(一个 `Status` 类型的值)赋值给了 `initStatus` 变量。这个返回值表示 `InitList` 函数执行的结果,如果返回 `OK`(定义为 `1`),则表示函数执行成功。

所以,这行代码的目的是调用 `InitList` 函数来初始化 `myList`,并检查函数执行的结果是否成功。

顺序线性表L已存在,判定是否空表

/* 初始条件:顺序线性表L已存在。操作结果:若L为空表,则返回TRUE,否则返回FALSE */

bool ListEmpty(SqList L)
{ 
    if(L.length == 0)
        return true;
    else
        return false;
}
int main() 
{
    SqList L;
    int e;
    if (InitList(&L))  //这行代码的含义是“如果初始化顺序表L成功,那么执行if后面的代码块”。
    {
        cout << "初始化后,L是否为空:" << (ListEmpty(L) ? "是" : "否") << endl;
        for(int i = 1; i <= 5; i++)
            ListInsert(&L, i, i);
        cout << "插入1~5后,L是否为空:" << (ListEmpty(L) ? "是" : "否") << endl;
        ListTraverse(L);
    }

    if (ListDelete(&L, 3, &e)) 
    {
        cout << "删除第3个元素后,L是否为空:" << (ListEmpty(L) ? "是" : "否") << endl;
        ListTraverse(L);
    }

    return 0;
}


//为什么InitList函数用*L,ListEmpty函数用L ?

//InitList 函数的目的是初始化一个 SqList 对象,这涉及到修改对象的状态(在这种情况下,是修改 length 属性)。因此,我们需要传递一个指向 SqList 的指针* L,这样函数才能直接修改原始对象的状态。
//如果我们只传递 SqList 对象本身,函数将操作一个对象的副本,原始对象的状态将不会被改变。
//另一方面,ListEmpty 函数的目的是检查一个 SqList 对象是否为空,这并不需要修改对象的状态。因此,我们可以直接传递 SqList 对象 L。这样做的好处是可以避免使用指针,使代码更简单、更易于理解。

//`SqList *L`和`SqList L`的主要区别在于它们是不同类型的变量。`SqList *L`是一个指向`SqList`类型的指针,而`SqList L`是一个`SqList`类型的实例。
//当你使用`SqList* L`时,`L`是一个指向`SqList`类型的指针,你需要通过`- > `运算符来访问`SqList`中的成员,如`L- > length`。
//而当你使用`SqList L`时,`L`是一个`SqList`类型的对象,你可以直接通过`.`运算符来访问`SqList`中的成员,如`L.length`。
//两者的主要区别在于`SqList* L`可以动态地改变指向的对象,而`SqList L`在声明时就已经固定下来,不能改变。同时,指针`L`可以被设置为`NULL`,而对象`L`则始终会占用内存空间。

顺序线性表L已存在,将表重置为空表

bool ClearList(SqList *L)
{ 
    L->length = 0;
    return true;
}
int main() 
{
    SqList L;
    int e;

    if (InitList(&L)) 
    {
        for(int i = 1; i <= 5; i++)
            ListInsert(&L, i, i);
        cout << "插入1~5后,L中的元素为:";
        ListTraverse(L);
    }

    if (ClearList(&L) == OK) 
    {
        cout << "清空L后,L中的元素为:";
        ListTraverse(L);
    }
    return 0;
}

返回线性表中数据元素个数

int ListLength(SqList L)
{
	return L.length;
}

返回线性表中第i个数据元素的值

bool GetElem(SqList L,int i,int *e)   //GetElem 是一个函数,接收一个 SqList 类型的值 L,一个整型值 i,以及一个指向 int 类型的指针 e 作为参数。它返回一个 Status 类型的值。
{
    if(L.length == 0 || i < 1 || i > L.length)
        return false;
    *e = L.data[i-1];  //将 SqList L 中索引为 i-1 的元素值赋给指针 e 所指向的变量。

    return true;
}
int main() 
{
    SqList L;
    int e;
    if (InitList(&L)) 
    {
        for(int i = 1; i <= 5; i++)
            ListInsert(&L, i, i);
        cout << "插入1~5后,L中的元素为:";
        ListTraverse(L);
    }

    if (GetElem(L, 3, &e) == 1) 
    {
        cout << "获取第3个元素的值为:" << e << endl;
    }

    return 0;
}

返回线性表中第1个与e满足关系的数据元素的位序

int LocateElem(SqList L,int e)
{
    int i;
    if (L.length == 0)
        return false;

    for(i = 0;i < L.length;i++)
    {
        if (L.data[i] == e)
            break;
    }

    if(i >= L.length)
        return false;

    return i+1;
}

在线性表中第i个位置之前插入新的数据元素e,L的长度加1

bool ListInsert(SqList *L,int i,int e)
{ 
	int k;
	if (L->length == MAXSIZE)  /* 顺序线性表已经满 */
		return false;
	if (i < 1 || i > L->length+1)/* 当i比第一位置小或者比最后一位置后一位置还要大时 */
		return false;

	if (i <= L->length)        /* 若插入数据位置不在表尾 */
	{
		for(k = L->length-1;k >= i-1;k--)  /* 将要插入位置之后的数据元素向后移动一位 */
			L->data[k+1] = L->data[k];
	}
	L->data[i-1] = e;          /* 将新元素插入 */
	L->length++;

	return true;
}

int main()
{
    // 创建一个列表并添加一些元素
    SqList list;
    list.length = 5;
    for (int i = 0; i < list.length; i++)
        list.data[i] = i + 1;

    // 插入一个元素
    if (ListInsert(&list, 3, 10) == 1)  //ListInsert(&list, 3, 10):这是对 ListInsert 函数的调用。函数的参数是一个指向 list 的指针(&list),一个整数 3(表示要插入元素的位置),和一个整数 10(表示要插入的元素)
        cout<<"Element inserted successfully\n";
    else
        cout<<"Error inserting element\n";

    return 0;
}

删除线性表的第i个数据元素,并用e返回其值,线性表的长度减1

#include <iostream>
using namespace std;

const int MAX_SIZE = 100;

struct SqList
{
    int data[MAX_SIZE];
    int length;
};

bool ListDelete(SqList& L, int i, int& e)
{
    if (L.length == 0)
        return false;
    if (i < 1 || i > L.length)
        return false;

    e = L.data[i - 1];  //将顺序表中待删除元素的值保存到变量e中,以便在后续的输出中使用

    if (i < L.length)
    {
        for (int k = i; k < L.length; k++)
        {
            L.data[k - 1] = L.data[k];
        }
    }
    L.length--;
    return true;
}
int main()
{
    SqList list;
    list.length = 5;
    list.data[0] = 1;
    list.data[1] = 2;
    list.data[2] = 3;
    list.data[3] = 4;
    list.data[4] = 5;

    cout << "Before deletion: ";
    for (int i = 0; i < list.length; i++)
    {
        cout << list.data[i] << " ";
    }
    cout << endl;

    int position = 3;
    int deletedElement;
    bool result = ListDelete(list, position, deletedElement);

    if (result == true)
    {
        cout << "Element at position " << position << " (" << deletedElement << ") is deleted." << endl;
    }
    else
    {
        cout << "Deletion failed. Invalid position." << endl;
    }

    cout << "After deletion: ";
    for (int i = 0; i < list.length; i++)
    {
        cout << list.data[i] << " ";
    }
    cout << endl;

    return 0;
}

依次对线性表的每个数据元素输出

bool ListTraverse(SqList L)
{
	int i;
    for(i = 0;i < L.length;i++)
        visit(L.data[i]);
    cout<<" ";
    return true;
}

int main()
{
    // 创建一个列表并添加一些元素
    SqList list;
    list.length = 5;
    for (int i = 0; i < list.length; i++)
        list.data[i] = i + 1;

    // 遍历列表
    ListTraverse(list);

    return 0;
}

将所有的在线性表Lb中但不在La中的数据元素插入到La中

void unionL(SqList *La,SqList Lb)
{
	int La_len,Lb_len,i;
	int e;                        /*声明与La和Lb相同的数据元素e*/
	La_len = ListLength(*La);            /*求线性表的长度 */
	Lb_len = ListLength(Lb);
	for (i = 1;i <= Lb_len;i++)
	{
		GetElem(Lb,i,&e);              /*取Lb中第i个数据元素赋给e*/
		if (!LocateElem(*La,e))        /*La中不存在和e相同数据元素*/
			ListInsert(La,++La_len,e); /*插入*/
	}
}

int main()
{        
    SqList L;
	SqList Lb;
    
    int e;
    bool i;
    int j,k;
    i = InitList(&L);
    cout<<"初始化L后:L.length=%d\n",L.length;
    for(j = 1;j <= 5;j++)
        i = ListInsert(&L,1,j);
    cout<<"在L的表头依次插入1~5后:L.data=";
    ListTraverse(L); 

    cout<<"L.length=%d \n",L.length;
    i = ListEmpty(L);
    cout<<"L是否空:i=%d(1:是 0:否)\n",i;

    i = ClearList(&L);
    cout<<"清空L后:L.length=%d\n",L.length;
    i = ListEmpty(L);
    cout<<"L是否空:i=%d(1:是 0:否)\n",i;

    for(j = 1;j <= 10;j++)
        ListInsert(&L,j,j);
    cout<<"在L的表尾依次插入1~10后:L.data=";
    ListTraverse(L); 

    cout<<"L.length=%d \n",L.length;

    ListInsert(&L,1,0);
    cout<<"在L的表头插入0后:L.data=";
    ListTraverse(L); 
    cout<<"L.length=%d \n",L.length;

    GetElem(L,5,&e);
    cout<<"第5个元素的值为:%d\n",e;
    for(j = 3;j <= 4;j++)
    {
        k = LocateElem(L,j);
        if(k)
            cout<<"第%d个元素的值为%d\n",k,j;
        else
            cout<<"没有值为%d的元素\n",j;
    }
    

    k = ListLength(L); /* k为表长 */
    for(j = k+1;j >= k;j--)
    {
        i = ListDelete(&L,j,&e); /* 删除第j个数据 */
        if(i == 0)
            cout<<"删除第%d个数据失败\n",j;
        else
            cout<<"删除第%d个的元素值为:%d\n",j,e;
    }
    cout<<"依次输出L的元素:";
    ListTraverse(L); 

    j = 5;
    ListDelete(&L,j,&e); /* 删除第5个数据 */
    cout<<"删除第%d个的元素值为:%d\n",j,e;

    cout<<"依次输出L的元素:";
    ListTraverse(L); 

	//构造一个有10个数的Lb
	i = InitList(&Lb);
    for(j = 6;j <= 15;j++)
        i = ListInsert(&Lb,1,j);

	unionL(&L,Lb);

	cout<<"依次输出合并了Lb的L的元素:";
    ListTraverse(L); 

    return 0;
}

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值