本文利用Java语言实现对顺序表的模拟,下面先简单介绍下顺序表的相关概念:
顺序表:数据元素依次存储在一组地址连续的存储单元的线性表;
特性:顺序表用物理位置上的相邻来表示逻辑关系上相邻的两个元素,其存储位置可用一个简单、直观的公式来表示;
优缺点:便于实现元素的随机存取,但是在作插入或删除操作时需要移动大量元素;
1.线性表接口
因为考虑得到复用问题,所以未直接编写线性表的实现代码,此处先给出List接口的代码 ,其中注释摘自Java Platform SE 7,但是,仅对List接口中的部分方法进行模拟;
package org.sky.list;
public interface List<E> {
/*
* Returns the number of elements in this list.
* If this list contains more than Integer.MAX_VALUE elements, returns Integer.MAX_VALUE.
* @return the number of elements in this list
* @author sky
*/
int size();
/*
* Returns true if this list contains no elements.
* @return true if this list contains no elements
* @author sky
*/
boolean isEmpty();
/*
* Returns the element at the specified position in this list.
* @return the element at the specified position in this list
* @author sky
*/
E get(int index);
/*
* Inserts the specified element at the specified position in this list (optional operation).
* Shifts the element currently at that position (if any) and any subsequent elements to the right (adds one to their indices).
* @author sky
*/
void add(int index, E element);
}
2. 顺序表实现
下面给出顺序表ArrayList类的实现代码
package org.sky.list;
import java.util.Arrays;
import java.util.Collection;
public class ArrayList<E> implements List<E> {
/**
* 默认空表长度
*/
private final int initialCapacity = 10;
/**
* 用于保存顺序线性表的元素
*/
private Object[] objs;
/**
* 顺序表包含的元素个数
*/
private int size ;
/**
* the maximum size of array to allocate
*/
private static final int MAX_ARRAY_SIZE = Integer.MAX_VALUE - 8;
/**
* 构造默认长度为10的空表
*/
public ArrayList(){
objs = new Object[initialCapacity];
}
/**
* 构造指定长度的空表
* @param initialCapacity
*/
public ArrayList(int initialCapacity){
if(initialCapacity < 0){
try{
throw new Exception("Illegal initSize:" + initialCapacity);
}catch(Exception e){
e.printStackTrace();
}
}
objs = new Object[initialCapacity];
}
/**
* 构造包含特定集合的线性表
* @param c
*/
public ArrayList(Collection<? extends E> c){
objs = c.toArray();
size = objs.length;
if (objs.getClass() != Object[].class)
objs = Arrays.copyOf(objs, size, Object[].class);
}
/**
* 返回线性表中包含的元素个数
*/
public int size(){
return size;
}
/**
* 如果线性表中不包含任何元素则返回true
*/
public boolean isEmpty(){
return size == 0;
}
/**
* 返回线性表中指定位置的元素,如果越界,则返回异常
*/
@SuppressWarnings("unchecked")
public E get(int index){
if(index < 1 || index > size){
throw new IndexOutOfBoundsException("Index: "+index+", Size: "+size);
}
return (E) objs[index-1];
}
/**
* 在指定位置添加元素,如果越界,则返回异常
*/
public void add(int index, E element){
if(index<0 || index > size){
throw new IndexOutOfBoundsException("Index: "+index+", Size: "+size);
}
ensureCapacityInternal(size+1);
System.arraycopy(objs, index, objs, index + 1,
size - index);
objs[index] = element;
size++;
}
/**
* 确保插入元素后,数组长度依然满足,若不满足,则扩容
* @param minCapacity
*/
private void ensureCapacityInternal(int minCapacity)
{
// overflow-conscious code
int oldCapacity = objs.length;
int newCapacity = oldCapacity + (oldCapacity >> 1);
if (newCapacity - minCapacity < 0)
newCapacity = minCapacity;
if (newCapacity - MAX_ARRAY_SIZE > 0)
newCapacity = (minCapacity > MAX_ARRAY_SIZE) ? Integer.MAX_VALUE : MAX_ARRAY_SIZE;
// minCapacity is usually close to size, so this is a win:
objs = Arrays.copyOf(objs, newCapacity);
}
}
3 测试代码
package org.sky.list;
public class Test {
public static void main(String[] args) throws Exception{
ArrayList arraylist = new ArrayList();
arraylist.add(0, 1);
arraylist.add(1, 2);
System.out.println(arraylist.get(2));
}
}