我有一个结构不完全是跳过列表,但有些相似。 有一个节点列表,其中每个节点都有一个指向下一个节点的前向数组和一个指向前一个节点的向后数组,数组大小由节点的构造函数指定,并受其中的项数限制名单。数组中的每个插槽都是一个链接(当前节点指向的插槽),它指向下一个节点,该节点的数组大小大于或等于我当前所在的数组。 列表:
public class FloorsArrayList implements DynamicSet {
//@TODO: add fields
private int bound;
private int size;
private FloorsArrayLink ninf;
private FloorsArrayLink pinf;
private int roof;
/*
* create a list with positive and negative infinity nodes
* set a bound on the number of items in the list
* initiates array with values pointing forward at POSITIVE INFINITY for NEGATIVE INFINITY
* and values pointing backwards at NEGATIVE INFINITY for POSITIVE INFINITY
* */
public FloorsArrayList(int N){
//@TODO: implement
this.bound = N;
this.size = 0;
this.roof = 0;
ninf = new FloorsArrayLink(Double.NEGATIVE_INFINITY , N+1);
pinf = new FloorsArrayLink(Double.POSITIVE_INFINITY , N+1);
for(int i = ninf.getArrSize() ; i > 0 ; i-- ) {
ninf.setNext(i, pinf) ;
pinf.setPrev(i, ninf);
}
}
@Override
/*
* returns the number of items in the list.
* @return number of items in the list.
* */
public int getSize(){
//@TODO: implement
return size;
}
@Override
/*
* method that takes a key value and an array size value
* inserts a node with those value to the list in a sorted order
* by key ( small - large)
* updates , if needed , the size of the largest array in the list
* */
public void insert(double key, int arrSize){
//@TODO: implement
FloorsArrayLink toInsert = new FloorsArrayLink(key, arrSize);
int i = arrSize;
FloorsArrayLink curr = ninf;
FloorsArrayLink next = curr.getNext(i);
while(i>0) {
while( next.getKey() < key ) {
curr = next;
next = curr.getNext(i);
}
toInsert.setPrev(i, curr);
toInsert.setNext(i, next);
next.setPrev(i, toInsert);
curr.setNext(i, toInsert);
i=i-1;
if(i>0) {
next = curr.getNext(i);
}
}
if(arrSize > roof){
roof = arrSize;
}
size++;
}
@Override
/*
* removes existing node from the list and update the pointer values
* */
public void remove(FloorsArrayLink toRemove) {
//@TODO: implement
for(int i = 1; i<= toRemove.getArrSize(); i++){
(toRemove.getNext(i)).setPrev(i, toRemove.getPrev(i));
(toRemove.getPrev(i)).setNext(i, toRemove.getNext(i));
}
}
@Override
/*
* search for a node with the specified key value and return
* the node containing it . returns null if such node does not exist.
* @return a node with a specified key value.
* @return null if there is no such node.
* */
public FloorsArrayLink lookup(double key) {
//@TODO: implement
int i = roof;
FloorsArrayLink curr = ninf;
FloorsArrayLink next = curr.getNext(i);
while(i>=0) {
while( next.getKey() <= key ) {
curr = next;
next = curr.getNext(i);
}
i=i-1;
if(i>0) {
next = curr.getNext(i);
}
}
if(curr.getKey() == key) {
return curr;
}
return null;
}
@Override
/*
* returns the successor of a given link. returns NEGATIVE INFINITY
* if link does not have a successor.
* @return the successor of given link. @return NEGATIVE INFINITY if
* link has no successor.
* */
public double successor(FloorsArrayLink link) {
//@TODO: implement
if(link.getNext(1).getKey() != Double.POSITIVE_INFINITY ){
return link.getNext(1).getKey();
}
return Double.NEGATIVE_INFINITY;
}
@Override /*
* returns the predecessor of a given link. returns POSITIVE INFINITY
* if link does not have a predecessor.
* @return the predecessor of given link. @return POSITIVE INFINITY if
* link has no predecessor.
* */
public double predecessor(FloorsArrayLink link) {
//@TODO: implement
if(link.getPrev(1).getKey() != Double.NEGATIVE_INFINITY ){
return link.getPrev(1).getKey();
}
return Double.POSITIVE_INFINITY;
}
@Override
/*
* returns minimum key value from the list.
* @return minimum key value from the list.
* */
public double minimum() {
//@TODO: implement
if(size == 0){
return Double.POSITIVE_INFINITY;
}
return ninf.getNext(1).getKey();
}
@Override
/*
* returns maximum key value from the list.
* @return maximum key value from the list.
* */
public double maximum() {
//@TODO: implement
if(size == 0){
return Double.NEGATIVE_INFINITY;
}
return pinf.getPrev(1).getKey();
}
}
节点:
public class FloorsArrayLink {
//@TODO: add fields
private double key;
private int arrSize;
private FloorsArrayLink[] fArray;
private FloorsArrayLink[] bArray;
public FloorsArrayLink(double key, int arrSize){
//@TODO: implement
this.key = key;
this.arrSize = arrSize;
this.fArray = new FloorsArrayLink[arrSize];
this.bArray = new FloorsArrayLink[arrSize];
}
/*
* returns key value
* @return key value
* */
public double getKey() {
//@TODO: implement
return this.key;
}
/*
* returns the next node in the list on the same level as i.
* @return the next node in the list on the same level as i.
* */
public FloorsArrayLink getNext(int i) {
//@TODO: implement
return this.fArray[i-1];
}
/*
* returns the previous node in the list on the same level as i.
* @return the previous node in the list on the same level as i.
* */
public FloorsArrayLink getPrev(int i) {
//@TODO: implement
return this.bArray[i-1];
}
/*
* sets the next node in the list at level i to next.
* */
public void setNext(int i, FloorsArrayLink next) {
//@TODO: implement
if(i>this.arrSize) {
return;
}
fArray[i-1]=next;
}
/*
* sets the previous node in the list at level i to previous.
* */
public void setPrev(int i, FloorsArrayLink prev) {
//@TODO: implement
if(i>this.arrSize) {
return;
}
bArray[i-1]=prev;
}
/*
* return the size of the arrays storing the pointers.
* @return size of arrays storing the pointers.
* */
public int getArrSize(){
//@TODO: implement
return arrSize;
}
}
我了解所有在O(n)时间运行的insert,lookup和remove方法,但是现在我引入了一个新结构,该结构实际上说如果我在第i个节点,则数组大小将为x + 1其中x是使得i mod(2 ^ x)= 0的最小x 因此,例如对于第一个节点1 mod 2 ^ 0 = 0,则arraysize将为1;对于第8个节点,8 mod 2 ^ 3 = 0,因此数组大小将为4。 现在这个结构强加了O(log(n))时间复杂度,但是我在分析它时遇到了麻烦。有帮助吗?