线性表的链接存储结构及JAVA实现

单链表:是用一组任意的存储单元存放线性表的元素,这组存储单元可以连续也可以不连续,甚至可以零散的分布在内存中的任意位置。为了正确表示元素之间的逻辑关系,每个存储单元在存储数据元素的同时,还必须存储其后继元素所在的地址信息。其中data是数据域,,用来存放数据元素,next是指针域,用来存放该结点的后继结点的地址。

单链表的基本思想就是用指针表示结点之间的逻辑关系,首先要正确区分指针变量,指针、指针所指的结点和结点的值四个概念!

 显然,单链表中每个结点的存储地址存放在其前驱结点的next域中,而第一个元素无前驱,所以设头指针指向第一个元素所在结点(称为开始结点),整个单链表的存取必须从头开始进行,因而头指针具有标识一个单链表的作用;同时由于最后一个元素无后继,故最后一个元素所在的结点的指针域为空,即NULL,也称尾标志。

data

next

package data.LineList.LinkedList.SingleLinkedList;

public class SingleLinkedList<T> {
/**
 * 节点类
 * @author zhouhai
 *
 */	
class Node<T>{
	private T data;//数据域
	private Node next;//指针域保存着下一节点的引用
	Node(T data,Node next){
		this.data=data;
		this.next=next;
	}
	Node(T data){
		this(data,null);
	}
	Node(){
		
	}
	
}
/**
 * 下面是SingleLinkedList的成员变量和方法,
 */
private Node<T> head,tail;//头指针是没有数据(data)域的,只有next.尾标志(tail)的数据域为最后一个结点,next为null
/**
 * 无参构造方法
 */
public  SingleLinkedList(){

}
/**
 * 判断链表是否为空
 */
public  boolean isEmpty(){
	return head==null;
}
/**
 * 返回链表长度
 */
public int length(){
	Node<T> p=head;
	int len=0;
	while(p.next!=null){
		len++;
		p=p.next;
	}
	return len;
}
/**
 * 创建头指针,该方法只用一次
 */
public void addToHead(T item){
   head=new Node<T>();	
   head.next=null;
}
/**
 * 增加尾指针,该方法复用
 */
public void addToTail(T item){
	if(!isEmpty()){//若链表非空,将链表的尾指针的next初始化为一个新的元素
		tail.next=new Node<T>(item);
		tail=tail.next;
	}else{//如果为空,这创建一个新的,并将头尾同时指向他
		head=tail=new Node<T>(item);
	}
}
/**
 * 遍历打印整个链表
 *@Title: printList  
 *@Description: TODO 
 *@param       
 *@return void     
 *@throws
 */
public void printList(){
	if(isEmpty())throw new RuntimeException("该链表为空");
	else{
		Node node=head.next;//工作指针初始化(链表的第一个元素)
		while(node!=null){
			System.out.println(node.data);
			node=node.next;
		}
	}
}
/**
 * 在表头插入节点,效率非常高
 */
public  void addFirst(T item){
	Node<T> node=new Node<T>(item);
	node.next=head.next;
	head.next=node;
}
/**
 * 在表尾插入节点,效率低
 */
public void addLast(T item){
	Node<T> node=new Node<T>(item);
	Node<T> p=head;
	while(p.next!=null){
		p=p.next;
	}
	p.next=node;
	node.next=null;
}
/**
 * 在表头删除结点
 */
public  void  deleteFirst(){
	if(!isEmpty()){
		head.next=head.next.next;
	}else System.out.println("这是空表");
}
/**
 * 在表尾删除结点
 * 寻找链表最后一个结点,将倒数第二个结点的next指向null
 * ,则删掉了倒数第一个
 */
public  void deleteLast(){
	Node<T> curr=head,prev=null;
	while(curr.next!=null){
		prev=curr;
		curr=curr.next;
		if(curr.next==null)prev.next=null;
	}
}
/**
 * 返回链表第i(i>0)个元素
 */
public  Node<T> get(int i){
	if(i>length()||i<=0)throw new ArrayIndexOutOfBoundsException();
	else{
		Node<T> node=head.next;
		for(int j=1;j<i;j++){
			node=node.next;
		}
		return node;
	}
}
/**
 * 设置第i个元素的值为value
 *@Title: set  
 *@Description: TODO 
 *@param @param i
 *@param @param value      
 *@return void     
 *@throws
 */
public  void set(int i,T value){
	if(i<=0||i>length())throw new ArrayIndexOutOfBoundsException();
	else{
		Node p=head.next;
		for(int j=1;i<i;j++){
			p=p.next;
		}
		p.data=value;
	}
}
/**
 * 按值查找
 *@Title: indexOf  
 *@Description: TODO 
 *@param @param value      
 *@return void     
 *@throws
 */
public  int indexOf(T value){
	int index=0;
	Node p=head.next;
   for(;p!=null;p=p.next){
	   index++;
	   if(p.data==value)return index;
   }
   return -1;
}
/**
 * 是否包含值为value的元素
 *@Title: contains  
 *@Description: TODO 
 *@param @param value
 *@param @return      
 *@return boolean     
 *@throws
 */
public boolean contains(T value){
  return indexOf(value)!=-1;
}
/*
 * 在链表的第i个位置插入元素vlaue
 */
public void  insert(int i,T value){
	Node node=new Node(value);
	Node p=head.next;
	for(int j=1;j<i-1;j++){
		p=p.next;
	}
    //找到i-1个结点p,将node元素插在P后面
	node.next=p.next;
	p.next=p;	
 }
/*
 * 删除第i个元素
 */
public void delete(int i){
	Node p=head.next;
	for(int j=1;j<i-1;j++){
		p=p.next;
	}
	p.next=p.next.next;
 }
}



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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值