用java写链表简直爽歪歪
我中有你,你中有我
package task4_14;
interface Link {//接口,放各种链表操作的方法
void add (Object obj);
boolean remove (int index);
int indexOf(Object obj);
boolean set(int index,Object obj);
Object get(int index);
int length();
void clear();
Object[] toArray();
void printLink();
}
class Factory {//工厂类,简化main函数,直接调用Factor类产生一个链表
private Factory() {}
public static Link getLinkInstance() {//产生链表对象
return new LinkImpl();
}
}
class LinkImpl implements Link {//产生链表的类,继承了接口
private int size = 0;//链表长度
private Node first;//头头结点
private Node last;//尾巴节点
private class Node {//产生节点的方法
private Object item;//存放元素
private Node next;//前一个节点
private Node prev;//后一个节点
private Node(Node prev,Object item,Node next) {//产生节点的构造方法,用private私有化,在本类中产生
this.item = item;
this.next = next;//后节点
this.prev = prev;//前节点
}
}
@Override
public void add(Object obj) {//增加节点,这儿有点绕=.=
Node tmp = this.last;//先把尾节点存起来
Node newNode = new Node(tmp, obj, null);//产生一个新节点,里面的头结点放了当前的尾节点
this.last = newNode;//先放进去,尾节点都要放的,这样,每次都是尾巴,逃不了....惨
if (null == tmp) {//空的,第一次加节点
this.first = newNode;//给头结点,以后找后面的节点就靠你了
}else {
tmp.next = newNode;//不是空的,就放到.next里
}
this.size++;
}
@Override
public boolean remove(int index) {//移除下标为index的对象
Node tmp = this.first;//不能拿头结点随便玩,那个临时的玩
if(index <0 || index >this.size) {//判断下标是否合理
return false;
}
while(0 !=index--){//合理,开始找啊
tmp = tmp.next;
}//铁定找到了
tmp.prev.next = tmp.next;//tmp前一个节点的.next指向tmp的下一个节点
tmp.next.prev = tmp.prev;//tmp的后一个节点的.prev指向tmp的上一个节点//tmp被抛弃
return true;
}
@Override
public int indexOf(Object obj) {//根据对象找下标
int i = 0;
Node tmp = this.first;//老规矩
if (obj == null) {//对象可能是null,没事放个null在链表里也是闲得慌
while (null != tmp) {//遍历链表
if (tmp.item == null) {//找null
return i;//找到了,送走
}
tmp = tmp.next;//下一个
i++;
}
}
else {
while (null != tmp) {//正常的
if (obj.equals(tmp.item)) {//注意这里,equals的这么用的,如果对象是null,NullPointException
return i;
}
tmp = tmp.next;
i++;
}
}
return -1;//查无此人
}
@Override
public boolean set(int index, Object obj) {//插呀...
Node tmp =this.first;
Node newNode = new Node(null, obj, null);//产生一个新节点
// Node newNode = null//错误的写法
// newNode.item = obj;
if(index <0 || index >this.size) {//下标合理否
return false;
}
while(0 !=index--){//找位置
tmp = tmp.next;
}
newNode.next =tmp.next;//新节点中存下一个节点的位置
tmp.next = newNode;//上一个加点中存新节点
newNode.prev =tmp;//新节点中存上一个节点的位置
newNode.next.prev = newNode;//下一个节点中存新节点
return true;
}
@Override
public Object get(int index) {//根据下标获取对象
Node tmp = this.first;
if(index <0 || index >this.size) {//下标合理否
return false;
}
while (0 !=index--) {//循环找
tmp = tmp.next;
}
return tmp.item;
}
@Override
public int length() {//链表长度
return this.size;//直接返回size
}
@Override
public void clear() {//清空链表
Node tmp = this.first;
while (null !=tmp) {//都得死,一个也跑不了
Node fina =tmp.next;
tmp.prev =null;
tmp.item =null;
tmp.next =null;
tmp = fina;
}//全部干掉
this.size =0;//置零
this.last = null;
this.first = null;//你俩也得死
}
@Override
public Object[] toArray() {//链表转对象数组
int i = 0;
Node tmp = this.first;
Object[] num= new Object[this.size];//看,数组这么用的//创建一个链表那么长的对象数组
while(null !=tmp) {//放进去
num [i] = tmp.item;
tmp = tmp.next;
i ++;
}
while (0 != i--) {//看看放进去没,正好用i吧,不过是倒序
System.out.println(num[i]);
}
return num;
}
@Override
public void printLink() {//打印链表
Node tmp = this.first;
while (null != tmp) {
System.out.println(tmp.item);
tmp =tmp.next;
}
}
}
public class Test {//主类
public static void main(String[] args) {
Link link = Factory.getLinkInstance();//调用工厂类的getter方法产生一个链表
//以下都是测试
//+++++++++++++++++++ 我是分割线+++++++++++++++++++
link.add("0");
link.add("1");
link.add(null);
link.add("2");
link.add("3");
link.add("4");
/*测试length(),indexOf(),indexOf(null);
System.out.println(link.length());
System.out.println(link.indexOf("2"));
System.out.println(link.indexOf("1"));
System.out.println(link.indexOf(null));
*/
// link.printLink();//打印链表
// System.out.println("++++++++++++");
// link.remove(1);
// link.printLink();//打印链表
// System.out.println(link.indexOf("4"));
// System.out.println(link.get(2));//获取下标元素
//测set
// link.printLink();//打印链表
// System.out.println("++++++++++++");
// link.set(1, "2");
// link.printLink();//打印链表
//测clear
// link.printLink();
// link.clear();
// System.out.println("+++++++++++++++++");
// link.printLink();
link.printLink();
System.out.println("+++++++++++++++++");
link.toArray();
}
}
//+++++++++++++++++++++++++++++++++++++++==