对于ArrayList类是顺序表结构,底层是数组实现。虽然在初始化时可以赋值容量,但容量只是数组的容量初始化,而非元素的个数size。那么在对顺序表进行add(index, element)选择索引添加操作时,它的索引值比较的不是超过底层数组的容量,而是比较的元素个数size。这应该是Java实现顺序表数据结构的特点。
使用数组存储三元组和ArrayList顺序表存储在快速转置中的区别,以及发现的ArrayList顺序表的add()方法需要rangeCheck检查的特点。
- 三元组稀疏矩阵类中使用数组存储:
public class SparseMatrix {
private TripleNode data[]; //三元组表
private int rows; //行数
private int cols; //列数
private int nums; //非零元素个数
}
- 则在快速转置中的代码:
public SparseMatrix fasttranspose() {
SparseMatrix tm = new SparseMatrix(cols,rows,nums);
int j=0,k=0;
num=new int[cols];
for (i=0; i<nums; i++) {
j= data[t].getColumn()];
num[j]++;
}
cpot=new int[cols];
cpot[0] = 0;
for (i=1; i<cols; i++)
cpot[i] = cpot[i-1] + num[i-1];
for (i=1; i<=nums; ++i) {
j = data[i].getColumn();
b.data[cpot[j]] = new TupElem(data[i].c,data[i].r,data[i].value);
cpot[j]++; //该列下一个非零元的存放位置
}
}
}
- 而使用ArrayList作为三元组的存储数据类型:
public class TupClass{
ArrayList<TupElem> data; //稀疏矩阵对应的三元组顺序表
int rows; //行数
int cols; //列数
int nums; //非零元素个数
}
则在快速转置中的代码:
public TupClass fastTranspose() {
TupClass b = new TupClass(cols,rows,nums);
// 扩充设置size,否则出现索引越界异常
for(int i = 0;i<b.nums;i++)
b.data.add(new TupElem(0,0,0));
int j = 0, k = 0;
// num[col]存放矩阵a中第col列的非零元素的个数
int[] num = new int[cols];
for(int col=0;col<cols;col++){
num[col]=0;
}
for (int i=0; i<a.nums; i++) {
j = data.get(i).c;
num[j]++;
}
// cpot[col]存放矩阵a中第col列的第一个非零元素在data顺序表中的位置
int[] cpot = new int[cols];
cpot[0] = 0;
for (int i=1; i<cols; i++)
cpot[i] = cpot[i-1] + num[i-1];
//找非零元素转置
for (int i=1; i<b.nums; i++) {
j = data.get(i).c;
//行列交换转置
b.data.add(cpot[j], new TupElem(data.get(i).c,data.get(i).r,
data.get(i).value));
cpot[j]++; //该列下一个非零元的存放位置
}
return b;
}
多一段代码的原因:
使用ArrayList顺序表而不是用数组存储三元组,需要注意一个问题,就是:扩充设置size,否则在转置for循环中由于add()方法不是从索引0开始添加的,会出现索引越界异常。
原因在于:add(index,element)方法时,存在检查机制ArrayList.rangeCheckFor
Add()使得index不能超过size。
这说明:ArrayList中的rangeCheck是与集合内的元素总数做比较,而不是与底层的数组长度做比较。
代码异常示例:
ArrayList类文件中的源码:
测试代码:
int[][] mat1 = {{0,0,0,1},{0,2,0,0},{0,0,3,1},{0,8,0,1},{4,0,0,0}};
TupClass tupClass = new TupClass(mat1);
System.out.println("三元组的稀疏矩阵1显示:");
tupClass.display();
System.out.println("其非零元素个数为:" + tupClass.nums);
//测试转置
System.out.println("========测试转置========");
TupClass tupClassT = TupClass.transpose(tupClass);
System.out.println("稀疏矩阵1的转置显示:");
tupClassT.display();
TupClass tupClassT1 = TupClass.fastTranspose(tupClass);
System.out.println("稀疏矩阵1的快速转置显示:");
tupClassT1.display();