首先:我不是要重新发明轮子,这是为了研究目的。
我是java世界的新手,所以请耐心等待。
我的目标是构建一个公共类来管理带有排序插入的链表。
到目前为止我做的(工作)是:
import java.util.Iterator;
import package_Car.SortTypes;
class Node<E>
{
E data;
Node<E> next;
Node(E data, Node<E> node)
{
this.data = data;
this.next = node;
}
public Node<E> getNext()
{
return next;
}
}
public class SortedInsertionLinkedList<E> implements Iterable<Node<E>>
{
Node<E> root;
Sort_Types sort;
final class LinkedListIterator implements Iterator<Node<E>>
{
private Node<E> cursor;
LinkedListIterator(Node<E> root)
{
cursor = new Node<E>(null, null);
cursor = root;
}
public boolean hasNext()
{
return cursor != null;
}
public Node<E> next()
{
Node<E> retVal = cursor;
if (hasNext())
{
cursor = retVal.getNext();
}
return retVal;
}
}
public Iterator<Node<E>> iterator()
{
return new LinkedListIterator(root);
}
public SortedInsertionLinkedList(Sort_Types sort)
{
root = null;
this.sort = sort;
}
public void insert(E item)
{
if (item != null)
{
if (root == null)
{
root = new Node<E>(item, null);
}
else
{
Node<E> currNode = root;
Node<E> prevNode = null;
for (Node<E> currListNode : this)
{
if (sort.compareTo(currListNode.data, item) < 0)
{
prevNode = currListNode;
currNode = currListNode.next;
}
}
Node<E> t = new Node<E>(item, currNode);
if (prevNode == null)
root = t;
else
prevNode.next = t;
}
}
}
public void print()
{
for (Node<E> currNode : this)
{
System.out.print(currNode.data + " ");
System.out.println();
}
System.out.println();
}
public boolean find(E x)
{
for (Node<E> currNode : this)
{
int c = sort.compareTo(currNode.data, x);
if (c == 0)
return true;
if (c > 0)
return false;
}
return false;
}
public void delete(E x)
{
Node<E> prevNode = null;
for (Node<E> currNode : this)
{
int c = sort.compareTo(currNode.data, x);
if (c == 0)
{
if (currNode == root)
{
root = currNode.next;
}
else
{
prevNode.next = currNode.next;
}
return;
}
if (c > 0)
return;
prevNode = currNode;
}
}
}
正如您所看到的,我在我的类中添加了一个私有字段,用于定义必须使用哪种类型的排序来比较链表节点。此排序类型是枚举
public enum Sort_Types
{
SORT_BY_NAME
{
public int compareTo(Object o1, Object o2)
{
Car item1 = (Car) o1;
Car item2 = (Car) o2;
return item1.nome.compareTo(item2.nome);
}
},
SORT_BY_PRICE
{
public int compareTo(Object o1, Object o2)
{
Car item1 = (Car) o1;
Car item2 = (Car) o2;
return Double.compare(item1.prezzo, item2.prezzo);
}
},
SORT_BY_GAIN
{
public int compareTo(Object o1, Object o2)
{
double gain1;
double gain2;
if (o1 instanceof CarSpecificInterface)
{
CarSpecificInterface dummy = (CarSpecificInterface) o1;
gain1 = dummy.gain();
}
else
{
throw new IllegalArgumentException();
}
if (o2 instanceof CarSpecificInterface)
{
CarSpecificInterface dummy = (CarSpecificInterface) o2;
gain2 = dummy.gain();
}
else
{
throw new IllegalArgumentException();
}
return Double.compare(gain2, gain1);
}
},
SORT_BY_URGENCY
{
public int compareTo(Object o1, Object o2)
{
double urgency1;
double urgency2;
if (o1 instanceof CarSpecificInterface)
{
CarSpecificInterface dummy = (CarSpecificInterface) o1;
urgency1 = dummy.urgency();
}
else
{
throw new IllegalArgumentException();
}
if (o2 instanceof CarSpecificInterface)
{
CarSpecificInterface dummy = (CarSpecificInterface) o2;
urgency2 = dummy.urgency();
}
else
{
throw new IllegalArgumentException();
}
return Double.compare(urgency2, urgency1);
}
};
public abstract int compareTo(Object o1, Object o2);
}
为什么我这样做?由于可用于实例化链表的类是3:
Car
New_Car
extends Car
Used_Car
extends Car
New_Car
和Used_Car
类实现了一个接口
public interface Car_Specific_Interface
{
public double gain();
public double urgency();
}
所以我可以将我的链表用于可以接受(显然)SubClasses
的Car类型Sorted_Linked_List<Car> carsSortedByName;
Sorted_Linked_List<Car> carSortedByGain;
Sorted_Linked_List<Car> carSortedByUrgency;
public DB_Mng()
{
carsSortedByName = new Sorted_Linked_List<>(Sort_Types.SORT_BY_NAME);
carSortedByGain = new Sorted_Linked_List<>(Sort_Types.SORT_BY_GAIN);
carSortedByGain = new Sorted_Linked_List<>(Sort_Types.SORT_BY_URGENCY);
}
所以,总结一下:我有一个带有排序插入的通用链表,可以接受不同的类,可以按特定的字段或方法排序。
我想要了解的是,是否有办法改变班级层次结构&#34;简单地说&#34;实施Comparable
接口。
答案 0 :(得分:1)
我建议完全退一步。使用Java8和lambdas以及流程,2017年确实会做出不同的事情。或者说,好几年。
我建议你从2014年斯图加特Java论坛中查看这个presentation。用德语开头几句,但其余的都是代码,很容易掌握。
事情是:你想写代码如下:
collection .sort(
Comparator
.comparing(Person::getName)
.reversed()
.thenComparing(Person::getId)
);
并使用lambdas /方法引用 - 而不是编写所有“手动样板”代码来访问成员字段,例如。
答案 1 :(得分:1)
第一步是了解java泛型。 特别, java泛型是一个编译时功能; 它们绝不是c ++模板的java实现。
您无法创建“完全通用”的插入排序列表,因为Object未实现任何比较功能。
您可以创建实现某些已知接口或扩展特定类的元素的插入排序列表。
答案 2 :(得分:1)
如果NewCar
和UsedCar
同时正在实施Car_Specific_Interface
,您只需检查比较器中的界面,例如:
if (o1 instanceof Car_Specific_Interface)
{
Car_Specific_Interface dummy = (Car_Specific_Interface) o1;
gain1 = dummy.gain();
}
else
{
throw new IllegalArgumentException();
}
您还可以让比较功能更复杂,以支持Comparable
和Comparator
。例如:
private int compareItems(E firstItem, E secondItem) {
if (sort == null) {
if (firstItem instanceof Comparable && secondItem instanceof Comparable) {
return ((Comparable)firstItem).compareTo(secondItem);
} else {
throw new IllegalArgumentException("Failed to compare");
}
}
return sort.compareTo(firstItem, secondItem);
}