码迷,mamicode.com
首页 > 其他好文 > 详细

顺序表实现增,删,查与合并操作

时间:2018-10-27 14:57:28      阅读:177      评论:0      收藏:0      [点我收藏+]

标签:rtl   逻辑   foreach   引用   struct   删除   数组越界   res   err   

C语言实现顺序表的的基本操作

1.顺序表实现按照位置查找

#include <stdio.h>
#include <stdlib.h>

#define MAX_SIZE 20

// 需求:
// 线性表查找之:按序号查找。
// 表中的元素是顺序存放的,故核心语句应该是l.elem[i-1]


// 定义一个顺序表
// 应该定义在外面,否则函数头声明访问不到
typedef struct{
    int elem[MAX_SIZE];
    int last;
} SeqList;


// 函数头声明
int getData(SeqList sl,int i);

void main(){

    int i;
    printf("请输入要查询元素的下标:");
    scanf("%d",&i);

    // 初始化并赋值
    SeqList sl = {{1,2,3,4,5},4};

    // 按照序号查找数组中的元素
    int a = getData(sl,i);
    printf("第%d个元素是:%d\n",i,a);
}

// 按照序号进行查找:getData(l,i),查找线性表中的第i个元素.
int getData(SeqList sl,int i){
    // 应该对数组是否越剧进行判断
    if(i<=0 || i>sl.last){
        printf("顺序表越界!\n");
        exit(0);
    }

    return sl.elem[i-1];
}

2.顺序表实现按照元素查找

#include <stdio.h>

// 需求:
// 按照内容查找,要求查找顺序表L中给定的值e相等的元素

# define MAX_SIZE 10

// 定义一个顺序表
typedef struct{
    int elem[MAX_SIZE];
    int last;
} SeqList;

// 声明函数头
int locate(SeqList sl,int e);

void main(){
    int index,e;
    printf("请输入要查找的元素:");
    scanf("%d",&e);
    // 初始化顺序表
    SeqList sl = {{9,8,7,6,5,4},5};
    index = locate(sl,e);
    printf("你查找的元素%d在第%d的位置。\n",e,index);
}

// 算法思想:从第一个元素开始,一次将表中的元素与e相比较,若相等,则返回元素在表中的序号;
// 若找不到,返回-1
int locate(SeqList sl,int e){
    int i=0;
    // 逐个遍历数组,如果没有到末尾或者没有找到,就一直遍历
    while( i<=sl.last && sl.elem[i]!=e ){
        i++;
    }
    // 没有到末尾,且找到元素,就返回所在的位置
    if( i<sl.last && sl.elem[i]==e ){
        return i+1;
    }
    // 没有找到就返回-1
    return -1;
}

3.顺序表实现删除元素

#include <stdio.h>

// 删除元素
// 这里给出的是根据元素进行删除
// 算法思想:判断当前是否是要删除的元,是就将下一个覆盖当前的,不是就当前的覆盖当前的


#define MAX_SIZE 20
#define OK 1
#define ERR 0

typedef struct {
    int elem[MAX_SIZE];
    int last;
} SeqList;

// 函数头
int deleteList(SeqList *sl, int e);

void foreach(SeqList sl);

int deleteList2(SeqList *sl, int e);

void main() {
    SeqList sl = {{2, 3, 4, 5, 6}, 5};
    // deleteList(&sl, 3);
    deleteList2(&sl, 3);
    foreach(sl);
}

// 这个是错误的,因为只能删除一次
// 算法思路:遍历数组,找到要删除的地方,然后删除之。删除后将数组后面的数据往前移动一个单位
int deleteList(SeqList *sl, int e) {
    for (int i = 0; i < sl->last; i++) {

        if (e == sl->elem[i]) {
            for (i; i < sl->last - 1; i++) {
                sl->elem[i] = sl->elem[i + 1];
            }
            sl->last = sl->last - 1;
            return OK;
        }
    }
    printf("元素%d不存在!", e);
    return ERR;
}

// 正确的删除思路,可以一次删除多个
// 不管有多少个都会被干掉
// 循环遍历数组,如果当前位置不是要删除的元素,就自己覆盖自己
// 如果是要删除的元素,就用下一个元素,覆盖当前元素
int deleteList2(SeqList *sl, int e) {
    int j = 0;
    int oldLast = sl->last;

    for (int i = 0; i < oldLast; i++) {
        // 只要不相等就覆盖当前的
        if (sl->elem[i] != e) {
            sl->elem[j] = sl->elem[i];
            j++;
        } else {
            sl->last--;    // 实现表尾指针的更新
        }

    }
}

// 遍历输出顺序表中的内容
void foreach(SeqList sl) {
    printf("所有的数据是:{");

    for (int i = 0; i < sl.last; i++) {
        if (i == (sl.last - 1)) {
            printf("%d}\n", sl.elem[i]);
        }
        printf("%d,", sl.elem[i]);
    }
}

4.顺序表实现添加元素

#include <stdio.h>

// 插入操作
// 是顺序表的节点的物理位置必须和逻辑位置保持一致
// 在插入的过程中,要将插入后的所有数据集体向后移动一位,以保持整体完整性
// 要注意:这里应该传入数组指针,而不是数组,因为C中的数组是值传递,不像java中是会直接修改值
// 算法的复杂度是:O((n-1)/2)

#define MAX_SIZE 20
#define OK 1
#define ERR 0

// 定义结构体
typedef struct{
    int elem[MAX_SIZE];
    int last;
} SeqList;

// 函数头
int insertList(SeqList sl,int e,int index);
void foreach(SeqList sl);
int insertList2(SeqList *sl,int e,int index);

void main(){
    // 初始化结构体
    SeqList sl = {{2,4,6,8,10},5};
    //int res = insertList(sl,3,2);
    int res = insertList2(&sl,3,2);
    printf("插入数据的返回值是:%d\n",res);
    foreach(sl);
}

// 这个是错误的,好像sl变成了引用传递。
int insertList(SeqList sl,int e,int index){
    // 数组越界
    if( index>=sl.last || index<0 ){
        printf("插入数据的位置不合法\n");
        return ERR;
    }
    if(sl.last>=MAX_SIZE-1){
        printf("数组的空间不够\n");
        return ERR;
    }

    int i = sl.last;
    while( i > (index-1) ){
        sl.elem[i] = sl.elem[i-1];
        i--;
    }

    if(i==(index-1)){
        sl.elem[i]=e;
        sl.last=sl.last+1;
        return OK;
    }

    return ERR;
}

// 遍历输出顺序表中的内容
void foreach(SeqList sl){
    printf("所有的数据是:{");

    for(int i=0;i<sl.last;i++){
        if(i==(sl.last-1)){
            printf("%d}\n",sl.elem[i]);
        }
        printf("%d,",sl.elem[i]);
    }
}

// 算法思想:
// 从数组最后开始遍历,将数据逐个往后移动,移动到给定的位置后,添加元素,并更新指针
int insertList2(SeqList *sl,int e,int index){
    // 数组越界
    if( index>=sl->last || index<0 ){
        printf("插入数据的位置不合法\n");
        return ERR;
    }
    if(sl->last>=MAX_SIZE-1){
        printf("数组的空间不够\n");
        return ERR;
    }
    // 从最后开始遍历数组,如果没有到给定的位置,就逐个的往后移动
    int i = sl->last;
    while( i > (index-1) ){
        sl->elem[i] = sl->elem[i-1];
        i--;
    }
    // 如果到了指定的位置,就添加,并且更新last指针的值
    if(i==(index-1)){
        sl->elem[i]=e;
        sl->last=sl->last+1;
        return OK;
    }

    return ERR;
}

5.顺序表实现合并操作

#include <stdio.h>

#define ElemType int
#define MAX_SIZE 20
#define OK 1
#define ERR 0

// 定义结构体
typedef struct {
    ElemType elem[MAX_SIZE];
    int last;
} SeqList;

// 函数头
void foreach(SeqList sl);
int mergeList(SeqList *l1, SeqList *l2, SeqList *l3);


void main() {
    SeqList l1 = {{1, 3, 4, 5}, 4};
    SeqList l2 = {{2, 6, 8, 10, 11}, 5};
    SeqList l3;

    mergeList(&l1, &l2, &l3);
    foreach(l3);


}

// 合并顺序表
// 比较逐个遍历a,b表,当前位置谁小就把谁写入c表中。大的放到下一轮比较中
// 最后逐个将还有数据的表写入到c表中
int mergeList(SeqList *l1, SeqList *l2, SeqList *l3) {
    int i, j, k;
    i = 0;
    j = 0;
    k = 0;

    while (i < l1->last && j < l2->last) {
        if (l1->elem[i] <= l2->elem[j]) {
            l3->elem[k] = l1->elem[i];
            j--;
        } else {
            l3->elem[k] = l2->elem[j];
            i--;
        }
        i++;
        j++;
        k++;
    }

    while (i < l1->last) {
        l3->elem[k] = l1->elem[i];
        i++;
        k++;
    }

    while (j < l1->last) {
        l3->elem[k] = l2->elem[j];
        j++;
        k++;
    }

    l3->last = l2->last + l1->last - 1;

}


// 遍历输出顺序表中的内容
void foreach(SeqList sl) {
    printf("所有的数据是:{");

    for (int i = 0; i < sl.last; i++) {
        if (i == (sl.last - 1)) {
            printf("%d}\n", sl.elem[i]);
        }
        printf("%d,", sl.elem[i]);
    }
}

 

顺序表实现增,删,查与合并操作

标签:rtl   逻辑   foreach   引用   struct   删除   数组越界   res   err   

原文地址:https://www.cnblogs.com/yanghuabin/p/9860847.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!