常见三种:
1.线性表的顺序存储:可以用数组实现,优点指定id,获取数据(get)与修改数据(set)比较容易,时间复杂度为常数,但是对于插入与删除就比较麻烦,时间复杂度最少为O(1),最多为O(n),平均时间复杂度为O(n).
2.线性表单向链式存储:核心就是每个节点包含下一个节点的id,调用next获取下一个节点,这样的好处是,修改的时候只需要更改下一个节点的id就行了,缺点就是获取指定id的节点时需要遍历一遍,最坏的情况下时间复杂度为O(n),最好为常数,最终平均时间复杂度为O(n)。
节点node如下:
public class Node {
private int data;
private Node nextnode;
public int getData() {
return data;
}
public void setData(int data) {
this.data = data;
}
public Node getNextnode() {
return nextnode;
}
public void setNextnode(Node nextnode) {
this.nextnode = nextnode;
}
}
下面简单的实现单向线性链表:
public class MyLinkList {
private int length = 0;
private Node mNode0;// 第一个node,链表数据为0 nextnode 为null
private Node mNextNode;
public MyLinkList() {
mNode0 = new Node();
}
public int getLength() {
return length;
}
public void addNode(Node node) {
if (mNode0.getNextnode() == null) {
mNextNode = node;
mNode0.setNextnode(mNextNode);
}
mNextNode.setNextnode(node);
mNextNode = node;
length++;
}
public void addNode(int position,Node node) {
Node pNode;
Node lNode;
if(position>=1)
{
pNode=getNode(position-1);
lNode=pNode.getNextnode();
pNode.setNextnode(node);
node.setNextnode(lNode);
}
else
{
Node firstnode=getFirstNode();
mNode0.setNextnode(node);
node.setNextnode(firstnode);
}
length++;
}
public Node getNode(int position)
{
int p=0;
Node pNode=mNode0.getNextnode();
while(p<position)
{
pNode=pNode.getNextnode();
p++;
}
return pNode;
}
public Node getFirstNode() {
return mNode0.getNextnode();
}
public Node getLastNode() {
return mNextNode;
}
}
测试:
public static void main(String[] args) {
Node n0=new Node();
n0.setData(0);
Node n1=new Node();
n1.setData(1);
Node n2=new Node();
n2.setData(2);
Node n3=new Node();
n3.setData(3);
Node n4=new Node();
n4.setData(4);
n0.setNextnode(n1);
n1.setNextnode(n2);
n2.setNextnode(n3);
n3.setNextnode(n4);
MyLinkList linkList=new MyLinkList();
linkList.addNode(n0);
linkList.addNode(n1);
linkList.addNode(n2);
linkList.addNode(n3);
linkList.addNode(0, n4);
for(int i=0,size=linkList.getLength();i<size;i++)
{
System.out.println("p-"+i+"node():"+linkList.getNode(i).getData());
}
System.out.println("length:"+linkList.getLength());
System.out.println("first node:"+linkList.getFirstNode().getData());
System.out.println("last node:"+linkList.getLastNode().getData());
}
打印结果如下:
p-0node():4
p-1node():0
p-2node():1
p-3node():2
p-4node():3
length:5
first node:4
last node:3
3.
线性链表的双向存储:单向存储只能往下遍历,因为只有next指针获取下一个节点,双向存储就是每个节点保留一个pre指针指向上一个节点,优缺点与单向存储是一样的。
public class Node {
private int data;
private Node nextnode;
private Node prenode;}
public class MyLinkList {
private int length = 0;
private Node mNode0;// 第一个node,链表数据为0 nextnode 为null
private Node mNextNode;
private Node mPreNode;
public MyLinkList() {
mNode0 = new Node();
}
public int getLength() {
return length;
}
public void addNode(Node node) {
if (mNode0.getNextnode() == null) {
mNextNode = node;
mPreNode=null;
node.setPrenode(mPreNode);
mNode0.setNextnode(mNextNode);
}
node.setPrenode(mNextNode);
mNextNode.setNextnode(node);
mNextNode = node;
length++;
}
public void addNode(int position,Node node) {
Node pNode;
Node lNode;
if(position>=1)
{
pNode=getNode(position-1);
lNode=pNode.getNextnode();
node.setPrenode(pNode);
node.setNextnode(lNode);
lNode.setPrenode(node);
pNode.setNextnode(node);
node.setNextnode(lNode);
}
else
{
Node firstnode=getFirstNode();
mNode0.setNextnode(node);
node.setNextnode(firstnode);
firstnode.setPrenode(node);
node.setPrenode(null);
}
length++;
}
public Node getNode(int position)
{
int p=0;
Node pNode=mNode0.getNextnode();
while(p<position)
{
pNode=pNode.getNextnode();
p++;
}
return pNode;
}
public Node getFirstNode() {
return mNode0.getNextnode();
}
public Node getLastNode() {
return mNextNode;
}
}
public static void main(String[] args) {
Node n0=new Node();
n0.setData(0);
Node n1=new Node();
n1.setData(1);
Node n2=new Node();
n2.setData(2);
Node n3=new Node();
n3.setData(3);
Node n4=new Node();
n4.setData(4);
n0.setNextnode(n1);
n1.setNextnode(n2);
n2.setNextnode(n3);
n3.setNextnode(n4);
MyLinkList linkList=new MyLinkList();
linkList.addNode(n0);
linkList.addNode(n1);
linkList.addNode(n2);
linkList.addNode(n3);
linkList.addNode(0, n4);
for(int i=linkList.getLength()-1;i>=0;i--)
{
System.out.println("p-"+i+"node():"+linkList.getNode(i).getData());
}
System.out.println("length:"+linkList.getLength());
System.out.println("first node:"+linkList.getFirstNode().getData());
System.out.println("last node:"+linkList.getLastNode().getData());
Node n=linkList.getLastNode();
System.out.println("pre node:"+n.getPrenode().getData());
System.out.println("pre node:"+n.getPrenode().getPrenode().getData());
System.out.println("pre node:"+n.getPrenode().getPrenode().getPrenode().getData());
}
打印如下:
p-4node():3
p-3node():2
p-2node():1
p-1node():0
p-0node():4
length:5
first node:4
last node:3
pre node:2
pre node:1
pre node:0