zoukankan      html  css  js  c++  java
  • c++(非STL)实现线性表

    c++(非STL)实现线性表

    这里注意一个问题
    关于涉及地址的函数定义和引用

    //初始化一个空的线性表
    Status InitList(SqList *L)     这里是*L
    {
    	L->elem = (Elemtype *) malloc(INIT_SIZE * sizeof(Elemtype));
    	if(!L->elem)
    	{
    		return ERROR;
    	}
    	L->length = 0;
    	L->size = INIT_SIZE;
    	return OK;
    } 
     这里是*L
    引用函数的时候
    InitList(&L);   传L的地址
    
    如果是Status InitList(SqList &L) 这就是c++特有的一种方式(具体叫什么我忘了,好像是引用)
    调用函数的时候   InitList(L);
    

    代码明天早上我敲上来

    #include<iostream>
    #include<algorithm>
    #include<stdlib.h>
    using namespace std;
    #define TRUE 1
    #define FALSE 0
    #define OK 1
    #define ERROR 0
    #define INIT_SIZE 10   //初始化表长 
    #define INCREMENT_SIZE 5   //分配增量
    /** 
    c语言中并没有status这个关键字,
    但是一般会定义这样一个类型,
    表示成功或者失败的状态 
    **/
    typedef int Status;
    typedef int Elemtype;
    //#define Status int 
    //#define Elemtype int 
     
    //定义线性表结构 
    typedef struct
    {
    	Elemtype *elem;  //存储空间基址
    	int length;   //当前长度
    	int size;    //当前分配的表长大小 
    }SqList;
    
    //初始化一个空的线性表
    Status InitList(SqList *L)
    {
    	L->elem = (Elemtype *) malloc(INIT_SIZE * sizeof(Elemtype));
    	if(!L->elem)
    	{
    		return ERROR;
    	}
    	L->length = 0;
    	L->size = INIT_SIZE;
    	return OK;
    } 
    
    //销毁线性表
    Status DestroyList(SqList *L)
    {
    	free(L->elem);
    	L->length = 0;
    	L->size = 0;
    	return OK;
    }
    
    //清空线性表
    Status ClearList(SqList *L)
    {
    	L->length = 0;
    	return OK;
    } 
    
    //判断线性表是否为空
    Status isEmpty(const SqList L)   //const好像是不能改动 
    {
    	if(L.length == 0)
    	{
    		return TRUE;
    	}
    	else
    	{
    		return FALSE;
    	} 
    } 
    
    //获取长度
    Status getLength(const SqList L)
    {
    	return L.length;
    } 
    
    //根据位置获取元素
    Status GetElem(const SqList L,int i,Elemtype *e)  //最后这个Elemtype *e应该就是用来接收获取的这个元素的
    {
    	if(i<1||i>L.length)  //取第一个元素,就是在取第0个 
    	{
    		return ERROR;
    	}
    	*e = L.elem[i-1];   //这里直接对传进来的参数操作 
    	return OK;
    } 
    
    //比较两个元素是否相等(用于查找元素)
    Status compare(Elemtype e1,Elemtype e2)
    {
    	if(e1 == e2)
    	{
    		return 0;
    	}
    	else if(e1 < e2)
    	{
    		return -1;
    	}
    	else 
    	{
    		return 1;
    	}
    } 
    
    //查找元素(使用 判断两个元素是否相等)
    Status FindElem(const SqList L,Elemtype e,Status(*compare)(Elemtype, Elemtype)) 
    {
    	int i;
    	for(i=0;i<L.length;i++)
    	{
    		if(!(*compare)(L.elem[i],e))
    		{
    			return i+1;
    		}
    	}
    	if(i>=L.length)
    	{
    		return ERROR;
    	}
    }
    
    //查找前驱元素
    Status PreElem(const SqList L,Elemtype cur_e,Elemtype *pre_e)
    {
    	int i;
    	for(i=0;i<L.length;i++)
    	{
    		if(cur_e == L.elem[i])
    		{
    			if(i!=0)
    			{
    				*pre_e = L.elem[i-1];
    			}
    			else
    			{
    			 	return ERROR;
    			} 
    		}
    		if(i>=L.length)
    		{
    			return ERROR;
    		}
    	 } 
    } 
    
    //查找后继元素 
    Status NextElem(const SqList L, Elemtype cur_e, Elemtype *next_e)
    {
        int i;
        for (i = 0; i < L.length; i++)
        {
            if (cur_e == L.elem[i])
            {
                if (i < L.length - 1)
                {
                    *next_e = L.elem[i + 1];
                    return OK;
                }
                else
                {
                    return ERROR;
                }
            }
        }
        if (i >= L.length)
        {
            return ERROR;
        }
    }
    
    //插入元素
    Status InsertElem(SqList *L,int i,Elemtype e)
    {
    	Elemtype *newbase = NULL;
    	if(i<1||i>L->length+1)
    	{
    		return ERROR;
    	}
    	if(L->length >= L->size) //如果L现有的长度大于其分配的表长 
    	{
    		//realloc:在现有情况下分配(增加)线性表 
    		newbase = (Elemtype*)realloc(L->elem,(L->size+INCREMENT_SIZE)*sizeof(Elemtype));
    		if(!newbase)
    		{
    			return ERROR;
    		}
    		L->elem = newbase;
    		L->size += INCREMENT_SIZE;
    	} 
    	Elemtype *p = &L->elem[i-1];
    	Elemtype *q = &L->elem[L->length-1];
    	for(;q>=p;q--)
    	{
    		*(q+1) = *q;
    	}
    	*p = e;
    	++L->length;
    	return OK;
    } 
    
    //删除元素并返回其值
    Status DeleteElem(SqList *L,int i,Elemtype *e)
    {
    	if(i<1||i>L->length)
    	{
    		return ERROR;
    	}
    	Elemtype *p = &L->elem[i - 1];
    	*e = *p;   //被删除元素
    	//我感觉也可以不用取地址赋值,可以直接赋值 
    	for (; p < &L->elem[L->length]; p++)
        {
            *(p) = *(p + 1);
        }
        --L->length;
        return OK; 
    } 
    
    //访问元素
    void visit(Elemtype e)
    {
    	cout<<e;
    }
    
    //遍历线性表
    Status TraverseList(const SqList L,void(*visit)(Elemtype))
    {
    	for(int i=0;i<L.length;i++)
    	{
    		//为什么这里不用括起来取地址 
    		visit(L.elem[i]); 
    	}
    	return OK;
    } 
    
    //主函数测试
    int main()
    {
    	SqList L;   //实例化一个对象
    	if(InitList(&L)) 
    	{
    		Elemtype e;
    		cout<<"init success"<<endl;
    		for(int i=0;i<10;i++)
    		{
    			InsertElem(&L,i+1,i);
    		}
    		cout<<"length is "<<getLength(L)<<endl;
    		if (GetElem(L, 1, &e)) {
            	cout<<"The first element is "<<e<<endl;
            }
            else
            {
            	cout<<"element is not exist"<<endl;   
            }
            if (isEmpty(L))
            {
            	cout<<"list is empty"<<endl;
            }
            else
            {
                cout<<"list is not empty"<<endl;
            }
            TraverseList(L,visit); 
            cout<<L.elem[2]; 
    	}
    	return 0;
    }
    
  • 相关阅读:
    二叉排序树
    索引顺序表查找(分块查找)
    wpf中的窗口
    递归算法以及汉诺塔
    Net中资源存储的设置
    AutoResetEvent 和ManualResetEvent
    WPF:跨应用程序会话保持和还原应用程序范围的属性
    Base64编码及其作用
    WPF中的应用程序级别Application
    Ajax经典学习教材,IBM官方Ajax教材
  • 原文地址:https://www.cnblogs.com/serendipity-my/p/13789622.html
Copyright © 2011-2022 走看看