数据结构-线性表基本操作

本文介绍了线性表的特点、定义及其抽象数据类型,详细讲解了线性表的顺序存储结构和链式存储结构,特别是单链表的基本操作,包括插入、删除、合并、查找和长度计算。此外,还讨论了单链表在Java中的实现,并总结了数据结构面试中常见的单链表问题,如建立、打印、删除结点、排序和求中间结点等。
摘要由CSDN通过智能技术生成

线性结构的特点:
线性结构是最简单最直接的数据关系,数据元素之间一一对应。

线性表的概念

线性表是由n个类型相同数据元素的有限序列。

线性表的特点:

同一性:线性表是由同类数据元素组成的,每一个a必须是同一数据对象

有穷性:线性表是由有限个数据元素组成,表长度就是表中数据元素的个数

有序性:线性表中相邻数据元素之间存在着序偶关系

抽象数据类型的使用:

由于抽象数据类型定义了相应模型上的基本 运算集,可如同使用整形类型的加减乘除运算集合一样,只要列出线性表抽象数据类型LinearList 就可以直接使用其上的基本运算集

抽象数据类型的使用:

抽象数据类型一经定义,就可以多次使用
在实际问题中可利用线性表抽象数据类型的9种基本运算的组合实现对线性表进行合并、分拆、排序等多种需求。

1、线性结构的特点

线性结构是最简单、最基本的结构,数据元素间是一一对应关系。

2、线性表定义

是由n个数据元素的有限序列。除第一个和最后一个元素以外,其余的每个元素都只有唯一的直接前驱和直接后继。

3、线性表抽象数据类型定义

线性表ADT包括抽象数据类型的名称及数据元素、结构关系、基本操作集合三部分。

线性表的顺序存储结构

节点顺序存,节点线性化

类型和变量的区别:
例如:两室一厅就是一个类型的定义,是一个类型是一个规格,这样301,302 这种门牌号都可以使具有这种规格的空间,这就是变量。

自定义类型定义了一种规格,如顺序表的数据类型定义SeqList

typedef  struct
{
	ElemType elem[MAXSIZE]   //线性表占用的数组空间
	int last;				//线性表的最后一个元素在数组中的位置下标
	
}SeqList;

(2)变量是规格类型的具体空间,两种定义方式

  • 将L定义为 Seql list:类型的变量,如 Seqlist L 将顺序表定义为一个变量。使用的时候我们
    可通过属性访问方式L.elem[i-1]访问顺序表中序号为i的元素ai。

  • 将L定义为指向 Seqlist类型的指针变量,如 SeqList *L 可通过指针访问方式L->elem[i-1]访问顺序表中序号为i的元素ai。

类型是一种规格的定义,而变量是一种空间的定义。

线性表的基本运算

增删改查

在上面的定义中,我们通过一个结构体,进行了一个简单线性表的定义,我们在C语言或者C++z中可以通过一个结构体来进行定义,在Java中没有结构体,我么可以通过一个类来进行线性表的表示。

使用Java语言先定义一个线性表 ,然后我们再定义其中的基本操作

Java JDK中有ArrayList和LinkedList两个类很好的实现了顺序存储和链式存储。因此学习数据结构的最好方式是去研究JDK源码。

我们可以看一下Java中ArrayList和LinkedList的区别:

  1. ArrayList和LinkedList可想从名字分析,它们一个是Array(动态数组)的数据结构,一个是Link(链表)的数据结构,此外,它们两个都是对List接口的实现。ArrayList是数组队列,相当于动态数组;LinkedList为双向链表结构,也可当作堆栈、队列、双端队列

  2. 当随机访问List时(get和set操作),ArrayList比LinkedList的效率更高,因为LinkedList是线性的数据存储方式,所以需要移动指针从前往后依次查找。

  3. 当对数据进行增加和删除的操作时(add和remove操作),LinkedList比ArrayList的效率更高,因为ArrayList是数组,所以在其中进行增删操作时,会对操作点之后所有数据的下标索引造成影响,需要进行数据的移动。

  4. 从利用效率来看,ArrayList自由性较低,因为它需要手动的设置固定大小的容量,但是它的使用比较方便,只需要创建,然后添加数据,通过调用下标进行使用;而LinkedList自由性较高,能够动态的随数据量的变化而变化,但是它不便于使用。

下面使用Java实现一个顺序表

首先定义一个线性表,并定义线性表中的插入删除的相关的操作。


    package com.shunxubiao;
    
    /***
     * 
     * @author lei
     *
     */
    public class MyArrayList {
   
    	
    	//定义一个用来保存数据的数组
    	private Object arr[];	
    	//定义一个空数组,用来初始化空数组
    	private Object[] DEFAULT_EMPTY = {
   };
    	//数组的初始容量,我们可以参照ArrayList源码,数组的初始容量为10
    	private  static final int DEFAULT_SIZE = 10;
    	//数组的大小,也就是数组的最大容量
    	private int maxSize;
    	//定义线性表的大小,线性表的当前个数
    	private int size;
    	
    	//带参构造方法,提供能构造指定容量的空列表
    	
    	public MyArrayList(int inittalSize){
   
    		if (inittalSize > 0) {
   
    			this.arr = new Object[inittalSize];
    			this.maxSize = inittalSize;
    		}else if (inittalSize == 0) {
   
    			this.arr = DEFAULT_EMPTY;
    		}else {
   
    			throw new IllegalArgumentException("不能为负,非法容量"+inittalSize);
    		}
    	}
    	
    	//空参构造,用来初始化一个空数组
    	public MyArrayList(){
   
    		this.arr = DEFAULT_EMPTY;
    	}
    	   
    	
    }

    
    //往线性表中指定位置插入数据
	//在指定位置插入元素,首先就是需要判断插入位置是否正确,然后判断数组长度是否越界,
	//如果已经满了我们需要重新增加数组的长度,一般是增加1.5倍长度,ArrayList JDK源码中也是增加1.5倍的数组长度。
	//然后移动数组元素,空出需要插入的位置,最后把数据插入到数组中。


    //在数组的指定位置插入元素。
	public void insert(int i,Object elem){
   
		//首先判断数组插入的位置是否合法
		if (i < 0) {
   
			new IllegalArgumentException("插入位置不合法");
		}
		if(i > size){
   
			new IllegalArgumentException("插入位置越界,当前数组的大小为:"+size);
		}
		
		Object oldArr[];
		Object newArr[];//用来存放扩容后的容量
		//如果当前线性表中数组为满的,需要增加数组的存储空间
		if (i == maxSize) {
   		
			oldArr = arr;			
			newArr = new MyArrayList[(int) (maxSize*1.5)];
			//把旧数组中的元素赋值到新的数组中
			for (int j = 0; j < newArr.length; j++) {
   
				newArr[j] = oldArr[j];
			}			
			maxSize = (int) (maxSize*1.5);
			arr = newArr;
		}
		
		//如果插入的位置是最后一个元素,不需要移动元素
		if (i == size) {
   
			arr[i] = elem;
			size++;
			return;
		}
		
		//如果插入的不是最后一个位置,需要移动元素,先移动位置,空出带插入位置元素
		for (int j = size;j > i;j--) {
   
			arr[j] = arr[j-1];
		}
		//移动完之后,插入元素
		arr[i] = elem;
		size++;
		
		//查看数组中的元素
		for (int j = 0; j < arr.length; j
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值