1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
use matrix::BasicReadableMatrix;
use matrix::BasicWriteableMatrix;
use matrix::SparseMatrix;


pub struct SparseCRS {
	val: Vec<f32>,
	col_ind: Vec<usize>,
	row_ptr: Vec<usize>,
    columns: usize
}


impl SparseCRS {

	/// creates a new matrix
	pub fn new(rows: usize, columns: usize) -> SparseCRS {
		let m = SparseCRS{val: vec![], row_ptr: vec![0; rows+1], col_ind: vec![0], columns: columns};
		return m;
	}

	/// resizes the vector
	pub fn resize(&mut self, rows: usize, columns: usize) {
		self.val = vec![];
		self.row_ptr = vec![0; rows+1];
		self.col_ind = vec![0];
        self.columns = columns;
	}

}



impl BasicReadableMatrix for SparseCRS {

	/// returns the number of rows in the matrix
	fn get_rows(&self) -> usize {
		return self.row_ptr.len()-1;
	}

	/// returns the number of columns in the matrix
	fn get_columns(&self) -> usize {
		return self.columns;
	}

	/// returns the (i,j)-th element of the matrix
	fn get_element(&self, i: usize, j: usize)-> f32 {

		if i >= self.get_rows() || j >= self.get_columns() {
			panic!("access out of bounds");
		}
		
        for idx in self.row_ptr[i]..self.row_ptr[i+1]{
            if self.col_ind[idx] == j {
                return self.val[idx]
            }
        }
        
        // this bit is only reached if no element was found
		return 0.0
	}
}



impl BasicWriteableMatrix for SparseCRS {

	/// sets the (i,j)-th element of the sparse matrix 
	fn set_element(&mut self, i: usize, j: usize, new_value: f32) {

		if i >= self.get_rows() || j >= self.get_columns() {
			panic!("assignment out of bounds");
		}
		
        
        let idx: usize = self.row_ptr[i];

        for idx in self.row_ptr[i]..self.row_ptr[i+1]{
            if self.col_ind[idx] == j {
                self.val[idx] = new_value;
                return
            } else if self.col_ind[idx] > j {
                break;
            }
        }

        // non-null element doesn't exist, so let's add one
        self.col_ind.insert(idx, j);
        self.val.insert(idx, new_value);

        for row_id in i+1..self.row_ptr.len() {
            self.row_ptr[row_id] = self.row_ptr[row_id] + 1;
        }
	}

    /// sets all elements to zero
    fn set_zero(&mut self) {

        let rows = self.get_rows();
		self.val = vec![];
		self.row_ptr = vec![0; rows+1];
		self.col_ind = vec![0];
    }

}


impl SparseMatrix for SparseCRS {

    /// returns the number of non-null matrix elements
    fn nnz(&self) -> usize {
        return self.val.len();
    }

}