packageliner_list;importjava.util.Scanner;publicclassSqListTest{publicstaticvoidmain(String[]args)throwsException{SqListsq1=newSqList(10);sq1.insertAt(0,"a0");sq1.insertAt(1,"a1");sq1.insertAt(2,"a2");sq1.insertAt(3,"a3");sq1.insertAt(4,"a4");sq1.insertAt(5,"a5");intindex=sq1.indexOf("a2");if(index!=-1){System.out.println("a2's index is "+index+"!");}else{System.out.println("a5 is not in this SqList!");}sq1.display();sq1.remove(2);System.out.println("After remove:");sq1.display();SqListsq2=newSqList(10);Scannersc=newScanner(System.in);System.out.println("Please input element:");for(inti=0;i<8;i++){sq2.insertAt(i,sc.next());}sc.close();sq2.display();}}
运行我们的测试类,得到以下测试结果:
然后描述单链表,注意:我们推荐使用带头结点的单链表。这里总结以下关于头指针和头结点的问题:首先要清楚,head 就是头指针,毋庸置疑;如果有头结点的话,head 也头结点,这里头指针就是头结点,一般说成头指针指向头结点,而 head.next 是下标为 0 的元素,规定 head 是下标为-1 的元素;如果没有头结点的话,head 本是就是下标为 0 的元素,这里没有头结点,但是 head 还是头指针。下面我们来描述结点类,它由两部分组成,data 数据域和 next 指针域:
packageliner_list;importjava.util.Scanner;//关于头结点与头指针的问题//首先要清楚,head就是头指针,毋庸置疑//如果有头结点的话,head也头结点,这里头指针就是头结点,一般说成头指针指向头结点,而head.next是下标为0的元素,规定 head是下标为-1的元素//如果没有头结点的话,head本是就是下标为0的元素,这里没有头结点,但是head还是头指针//建议写带头结点的单链表,此类就是一个典例publicclassLinkListimplementsIList{publicNodehead;publicLinkList()// 无参构造方法,只构建头指针{head=newNode();}publicLinkList(intlen,booleanOrder)throwsException// 带有两个参数的构造方法,分别为表长和插入的方式,规定true表示尾插法,flase表示头插法{this();if(Order){createAtEnd(len);}else{createAtHead(len);}}publicvoidcreateAtHead(intn)throwsException// 头插法{Scannersc=newScanner(System.in);System.out.println("Please input element:");for(inti=0;i<n;i++){insertAt(0,sc.next());}// sc.close(); // 不要关闭输入流// display();}publicvoidcreateAtEnd(intn)throwsException// 尾插法{Scannersc=newScanner(System.in);System.out.println("Please input element:");for(inti=0;i<n;i++){insertAt(length(),sc.next());}// sc.close(); // 不要关闭输入流// display();}@Overridepublicvoidclear()// 置空链表{head.data=null;head.next=null;}@OverridepublicbooleanisEmpty()// 链表判空{returnhead.next==null;}@Overridepublicintlength()// 返回链表长度{Nodep=head.next;// p指向首结点intlength=0;while(p!=null){p=p.next;length++;}returnlength;}@OverridepublicObjectget(inti)throwsException{Nodep=head.next;intj=0;while(p!=null&&j<i)// 从首结点开始向后查找,直到p指向第i个结点或者p为空{p=p.next;// 指针后移j++;// 计数加1}if(i<0||p==null)// i小于0或者大于表长减1时抛出异常{thrownewException("Argument 'i' is out of range!");}returnp.data;}@OverridepublicintindexOf(Objectx)// 规定-1表示不在LinkList当中{Nodep=head.next;intindex=0;while(p!=null&&!p.data.equals(x)){p=p.next;index++;}if(p!=null){returnindex;}else{return-1;}}@OverridepublicvoidinsertAt(inti,Objectx)throwsException{Nodep=head;// 插入时从头结点开始,因为可以插入在下标0的位置,也可以插入在下标为表长位置intj=-1;while(p!=null&&j<i-1)// 找出下标为i-1的结点,即i结点的前驱{p=p.next;j++;}if(i<0||p==null)// i小于0或者i大于表长时抛出异常{thrownewException("Argument 'i' is out of range!");}Nodes=newNode(x);s.next=p.next;p.next=s;}@Overridepublicvoidremove(inti)throwsException{Nodep=head;intj=-1;while(p!=null&&j<i-1)// 找到下标为i-1的结点,即i结点的前驱{p=p.next;j++;}if(i<0||p.next==null)// 抛出条件为i小于0或者i大于表长-1,所以此处为p.next==null{thrownewException("Argument 'i' is out of range!");}p.next=p.next.next;}@Overridepublicvoiddisplay(){Nodep=head.next;System.out.println("****** LinkList ******");while(p!=null){System.out.print(p.data.toString()+" ");p=p.next;}System.out.println();System.out.println("*********************");}}
最后测试我们的单链表,使用 LinkListTest 类来做测试:
LinkListTest.java
1 2 3 4 5 6 7 8 910111213141516171819202122232425
packageliner_list;publicclassLinkListTest{publicstaticvoidmain(String[]args)throwsException{LinkListlinkList=newLinkList(10,true);linkList.remove(0);linkList.remove(1);linkList.remove(linkList.length()-1);System.out.println("After remove:");linkList.display();linkList.insertAt(linkList.length(),"a9");System.out.println("After insert:");linkList.display();intindex=linkList.indexOf("a2");if(index!=-1){System.out.println("a2's index is "+index+"!");}else{System.out.println("a2 is not in this LinkList!");}}}