Skip to content

Commit 2a01ce1

Browse files
authored
Merge pull request #8 from JetBrains-Research/vector-python
Vector for python-package
2 parents 0e23933 + d9e36ac commit 2a01ce1

File tree

1,189 files changed

+6625317
-6369494
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

1,189 files changed

+6625317
-6369494
lines changed

README.md

Lines changed: 14 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -18,15 +18,15 @@ The library provides C-compatible API, written in the GraphBLAS style.
1818
cuBool library C API. This package exports library features and primitives
1919
in high-level format with automated resources management and fancy syntax sugar.
2020

21-
**The primary library primitive** is a sparse boolean matrix. The library provides
22-
the most popular operations for matrix manipulation, such as construction from
23-
values, transpose, sub-matrix extraction, matrix-to-vector reduce, matrix-matrix
24-
element-wise addition, matrix-matrix multiplication and Kronecker product.
21+
**The primary library primitives** are sparse matrix and sparse vector of boolean values.
22+
The library provides the most popular operations for matrix manipulation,
23+
such as construction from values, transpose, sub-matrix/sub-vector extraction, matrix-to-vector reduce,
24+
element-wise addition, matrix-matrix, matrix-vector, vector-matrix multiplication, and Kronecker product.
2525

2626
**As a fallback** library provides sequential backend for mentioned above operations
2727
for computations on CPU side only. This backend is selected automatically
2828
if Cuda compatible device is not presented in the system. This can be quite handy for
29-
prototyping algorithms on a local computer for later running on a powerful server.
29+
prototyping algorithms on a local computer for later running on a powerful server.
3030

3131
**PyPI package web page** is following [link](https://pypi.org/project/pycubool/).
3232

@@ -36,20 +36,23 @@ prototyping algorithms on a local computer for later running on a powerful serve
3636
- Python package for every-day tasks
3737
- Cuda backend for computations
3838
- Cpu backend for computations
39-
- Matrix creation (empty, from data, with random data)
39+
- Matrix/vector creation (empty, from data, with random data)
4040
- Matrix-matrix operations (multiplication, element-wise addition, kronecker product)
41+
- Matrix-vector operations (matrix-vector and vector-matrix multiplication)
42+
- Vector-vector operations (element-wise addition)
4143
- Matrix operations (equality, transpose, reduce to vector, extract sub-matrix)
42-
- Matrix data extraction (as lists, as list of pairs)
43-
- Matrix syntax sugar (pretty string printing, slicing, iterating through non-zero values)
44+
- Vector operations (equality, reduce to value, extract sub-vector)
45+
- Matrix/vector data extraction (as lists, as list of pairs)
46+
- Matrix/vector syntax sugar (pretty string printing, slicing, iterating through non-zero values)
4447
- IO (import/export matrix from/to `.mtx` file format)
4548
- GraphViz (export single matrix or set of matrices as a graph with custom color and label settings)
46-
- Debug (matrix string debug markers, logging)
49+
- Debug (matrix string debug markers, logging)
4750

4851
### Platforms
4952

5053
- Linux based OS (tested on Ubuntu 20.04)
51-
- Windows (coming soon)
52-
- macOS (coming soon)
54+
- Windows (not tested yet)
55+
- macOS (not tested yet)
5356

5457
### Simple example
5558

cubool/sources/core/matrix.cpp

Lines changed: 0 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -40,11 +40,6 @@ namespace cubool {
4040
Matrix::Matrix(size_t nrows, size_t ncols, BackendBase &backend) {
4141
mHnd = backend.createMatrix(nrows, ncols);
4242
mProvider = &backend;
43-
44-
// By default marker is the address of the matrix
45-
std::stringstream s;
46-
s << this;
47-
mMarker = s.str();
4843
}
4944

5045
Matrix::~Matrix() {

cubool/sources/core/object.cpp

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,13 @@
2727

2828
namespace cubool {
2929

30+
Object::Object() {
31+
// By default marker is the address of the object
32+
std::stringstream s;
33+
s << this;
34+
mMarker = s.str();
35+
}
36+
3037
void Object::setDebugMarker(const char *marker) {
3138
CHECK_RAISE_ERROR(marker, InvalidArgument, "Null pointer marker string");
3239

cubool/sources/core/object.hpp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,7 @@ namespace cubool {
3232

3333
class Object {
3434
public:
35+
Object();
3536
void setDebugMarker(const char* marker);
3637
const char* getDebugMarker() const;
3738
index getDebugMarkerSizeWithNullT() const;

cubool/sources/core/vector.cpp

Lines changed: 0 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -40,11 +40,6 @@ namespace cubool {
4040
Vector::Vector(size_t nrows, BackendBase &backend) {
4141
mHnd = backend.createVector(nrows);
4242
mProvider = &backend;
43-
44-
// By default marker is the address of the vector
45-
std::stringstream s;
46-
s << this;
47-
mMarker = s.str();
4843
}
4944

5045
Vector::~Vector() {

cubool/sources/core/vector.hpp

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -65,9 +65,6 @@ namespace cubool {
6565
// Cached values by the set functions
6666
mutable std::vector<index> mCachedI;
6767

68-
// Marker for debugging
69-
std::string mMarker;
70-
7168
// Implementation handle references
7269
VectorBase* mHnd = nullptr;
7370
BackendBase* mProvider = nullptr;

cubool/sources/cuda/cuda_vector.cu

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -124,8 +124,8 @@ namespace cubool {
124124
index firstToCopy = region.front();
125125

126126
VectorImplType::container_type result(resultSize);
127-
thrust::copy(vec.m_rows_index.begin() + firstToCopy, vec.m_rows_index.begin() + firstToCopy + resultSize,
128-
result.begin());
127+
thrust::transform(vec.m_rows_index.begin() + firstToCopy, vec.m_rows_index.begin() + firstToCopy + resultSize,result.begin(),
128+
[i]__device__(index id) { return id - i; });
129129

130130
// Update this impl data
131131
mVectorImpl = std::move(VectorImplType(std::move(result), nrows, resultSize));

cubool/sources/cuda/kernels/spreduce.cuh

Lines changed: 9 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -143,7 +143,6 @@ namespace cubool {
143143
using VectorType = details::SpVector<IndexType, AllocType>;
144144

145145
VectorType operator()(const MatrixType& m) {
146-
auto nrows = m.m_rows;
147146
auto ncols = m.m_cols;
148147
auto nvals = m.m_vals;
149148

@@ -156,33 +155,34 @@ namespace cubool {
156155
__device__ (IndexType i) {
157156
auto j = colIndex[i];
158157

159-
atomicOr((mask + j).get(), (IndexType) 1);
158+
mask[j] = 0x1u;
160159
}
161160
);
162161

163162
// Count nnz of the vector
164163
auto resultSize = thrust::reduce(mask.begin(), mask.end(), (IndexType) 0);
165164

166165
ContainerType<index> result(resultSize);
167-
ContainerType<index> offsets(mask.size());
168-
169-
// Evaluate write offsets of the result
170-
thrust::exclusive_scan(mask.begin(), mask.end(), offsets.begin(), (IndexType) 0, thrust::plus<IndexType>());
166+
ContainerType<index> order(1);
167+
thrust::fill(order.begin(), order.end(), (IndexType) 0);
171168

172169
// For each value of the mask write in the result buffer if it not zero
173170
thrust::for_each(thrust::counting_iterator<IndexType>(0), thrust::counting_iterator<IndexType>(ncols),
174-
[mask = mask.data(), result = result.data(), offsets = offsets.data()]
171+
[mask = mask.data(), result = result.data(), order = order.data()]
175172
__device__ (IndexType i) {
176173
if (mask[i] > 0) {
177-
auto offset = offsets[i];
174+
auto offset = atomicAdd(order.get(), (IndexType) 1);
178175
auto colId = i;
179176

180177
result[offset] = colId;
181178
}
182179
}
183180
);
184181

185-
return VectorType(std::move(result), nrows, resultSize);
182+
// Sort values within vector
183+
thrust::sort(result.begin(), result.end());
184+
185+
return VectorType(std::move(result), ncols, resultSize);
186186
}
187187

188188
};

cubool/sources/sequential/sq_subvector.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -48,7 +48,7 @@ namespace cubool {
4848

4949
for (auto v: a.indices) {
5050
if (first <= v && v < last) {
51-
out.indices.push_back(v);
51+
out.indices.push_back(v - i);
5252
}
5353
}
5454
}

cubool/tests/test_library_api.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -76,7 +76,7 @@ cuBool_Status TransitiveClosure(cuBool_Matrix A, cuBool_Matrix* T) {
7676
return CUBOOL_STATUS_SUCCESS;
7777
}
7878

79-
TEST(cuBool, Example) {
79+
TEST(cuBool, TsExample) {
8080
cuBool_Matrix A = nullptr;
8181
cuBool_Matrix T = nullptr;
8282

cubool/tests/test_vector_misc.cpp

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -109,6 +109,12 @@ TEST(cuBool_Vector, Marker) {
109109

110110
ASSERT_EQ(cuBool_Initialize(CUBOOL_HINT_NO), CUBOOL_STATUS_SUCCESS);
111111
ASSERT_EQ(cuBool_Vector_New(&vector, m), CUBOOL_STATUS_SUCCESS);
112+
113+
ASSERT_EQ(cuBool_Vector_Marker(vector, nullptr, &size), CUBOOL_STATUS_SUCCESS);
114+
ASSERT_LE(size, BUFFER_SIZE);
115+
ASSERT_EQ(cuBool_Vector_Marker(vector, buffer, &size), CUBOOL_STATUS_SUCCESS);
116+
std::cout << "Default marker: " << buffer << std::endl;
117+
112118
ASSERT_EQ(cuBool_Vector_SetMarker(vector, marker), CUBOOL_STATUS_SUCCESS);
113119
ASSERT_EQ(cuBool_Vector_Marker(vector, nullptr, &size), CUBOOL_STATUS_SUCCESS);
114120
ASSERT_LE(size, BUFFER_SIZE);

cubool/utils/testing/vector.hpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -46,7 +46,7 @@ namespace testing {
4646

4747
for (auto v: index) {
4848
if (i <= v && v < (i + m))
49-
out.index.push_back(v);
49+
out.index.push_back(v - i);
5050
}
5151

5252
out.nrows = m;

python/README.md

Lines changed: 38 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -19,32 +19,35 @@ The library provides C-compatible API, written in the GraphBLAS style.
1919
cuBool library C API. This package exports library features and primitives
2020
in high-level format with automated resources management and fancy syntax sugar.
2121

22-
**The primary library primitive** is a sparse boolean matrix. The library provides
23-
the most popular operations for matrix manipulation, such as construction from
24-
values, transpose, sub-matrix extraction, matrix-to-vector reduce, matrix-matrix
25-
element-wise addition, matrix-matrix multiplication and Kronecker product.
22+
**The primary library primitives** are sparse matrix and sparse vector of boolean values.
23+
The library provides the most popular operations for matrix manipulation,
24+
such as construction from values, transpose, sub-matrix/sub-vector extraction, matrix-to-vector reduce,
25+
element-wise addition, matrix-matrix, matrix-vector, vector-matrix multiplication, and Kronecker product.
2626

2727
**As a fallback** library provides sequential backend for mentioned above operations
2828
for computations on CPU side only. This backend is selected automatically
2929
if Cuda compatible device is not presented in the system. This can be quite handy for
3030
prototyping algorithms on a local computer for later running on a powerful server.
3131

32-
## Features
32+
### Features
3333

3434
- C API for performance-critical computations
3535
- Python package for every-day tasks
3636
- Cuda backend for computations
3737
- Cpu backend for computations
38-
- Matrix creation (empty, from data, with random data)
38+
- Matrix/vector creation (empty, from data, with random data)
3939
- Matrix-matrix operations (multiplication, element-wise addition, kronecker product)
40+
- Matrix-vector operations (matrix-vector and vector-matrix multiplication)
41+
- Vector-vector operations (element-wise addition)
4042
- Matrix operations (equality, transpose, reduce to vector, extract sub-matrix)
41-
- Matrix data extraction (as lists, as list of pairs)
42-
- Matrix syntax sugar (pretty string printing, slicing, iterating through non-zero values)
43+
- Vector operations (equality, reduce to value, extract sub-vector)
44+
- Matrix/vector data extraction (as lists, as list of pairs)
45+
- Matrix/vector syntax sugar (pretty string printing, slicing, iterating through non-zero values)
4346
- IO (import/export matrix from/to `.mtx` file format)
4447
- GraphViz (export single matrix or set of matrices as a graph with custom color and label settings)
4548
- Debug (matrix string debug markers, logging)
4649

47-
## Simple example
50+
### Simple example
4851

4952
Create sparse matrices, compute matrix-matrix product and print the result to the output:
5053

@@ -64,7 +67,31 @@ b[2, 1] = True
6467
print(a, b, a.mxm(b), sep="\n")
6568
```
6669

67-
## Transitive closure example
70+
### Vector example
71+
72+
Create sparse matrix and vector, compute matrix-vector and vector-matrix products and print the result:
73+
74+
```python
75+
import pycubool as cb
76+
77+
m = cb.Matrix.empty(shape=(3, 4))
78+
m[0, 1] = True
79+
m[1, 0] = True
80+
m[1, 3] = True
81+
m[2, 2] = True
82+
83+
v = cb.Vector.empty(nrows=4)
84+
v[0] = True
85+
v[2] = True
86+
87+
t = cb.Vector.empty(nrows=3)
88+
t[0] = True
89+
t[2] = True
90+
91+
print(m.mxv(v), t.vxm(m), sep="\n")
92+
```
93+
94+
### Transitive closure example
6895

6996
Compute the transitive closure problem for the directed graph and print the result:
7097

@@ -88,7 +115,7 @@ while total != t.nvals:
88115
print(a, t, sep="\n")
89116
```
90117

91-
## GraphViz example
118+
### GraphViz example
92119

93120
Generate GraphViz graph script for a graph stored as a set of adjacency matrices:
94121

0 commit comments

Comments
 (0)