LMMC
Lamina Mathematic core
载入中...
搜索中...
未找到
sparse_internal.h
浏览该文件的文档.
1
10#ifndef LMMC_SPARSE_INTERNAL_H
11#define LMMC_SPARSE_INTERNAL_H
12
13#include <stddef.h>
14#include <string.h>
15
16#include "internal.h"
17#include "memory_bridge.h"
18#include "lmmc/config.h"
19#include "lmmc/sparse.h"
20
21
22static inline lmmc_status_t lmmc_sparse_validate_outer(
23 const lmmc_sparse_mat_t* sparse, size_t outer_size) {
24 if (sparse->row_ptr[0] != 0 || sparse->row_ptr[outer_size] != sparse->nnz) {
26 }
27 for (size_t i = 0; i < outer_size; ++i) {
28 if (sparse->row_ptr[i] > sparse->row_ptr[i + 1] ||
29 sparse->row_ptr[i + 1] > sparse->nnz) {
31 }
32 }
33 return LMMC_STATUS_OK;
34}
35
36static inline lmmc_status_t lmmc_sparse_validate_inner(
37 const lmmc_sparse_mat_t* sparse, size_t outer_size, size_t inner_limit) {
38 for (size_t i = 0; i < outer_size; ++i) {
39 for (size_t p = sparse->row_ptr[i]; p < sparse->row_ptr[i + 1]; ++p) {
40 if (sparse->col_idx[p] >= inner_limit ||
41 (p > sparse->row_ptr[i] && sparse->col_idx[p - 1] >= sparse->col_idx[p])) {
43 }
44 }
45 }
46 return LMMC_STATUS_OK;
47}
48
49static inline lmmc_status_t lmmc_sparse_validate(const lmmc_sparse_mat_t* sparse) {
50 size_t outer_size = 0;
51 size_t inner_limit = 0;
52
53 if (sparse == NULL || sparse->row_ptr == NULL) {
55 }
56 if ((sparse->format != LMMC_SPARSE_CSR && sparse->format != LMMC_SPARSE_CSC) ||
57 sparse->rows == 0 || sparse->cols == 0) {
59 }
60 if (sparse->nnz > 0 && (sparse->col_idx == NULL || sparse->values == NULL)) {
62 }
63
64 if (sparse->format == LMMC_SPARSE_CSR) {
65 outer_size = sparse->rows;
66 inner_limit = sparse->cols;
67 } else {
68 outer_size = sparse->cols;
69 inner_limit = sparse->rows;
70 }
71
72 const lmmc_status_t status = lmmc_sparse_validate_outer(sparse, outer_size);
73 if (status != LMMC_STATUS_OK) {
74 return status;
75 }
76 return lmmc_sparse_validate_inner(sparse, outer_size, inner_limit);
77}
78
79
80
81static inline lmmc_status_t lmmc_sparse_storage_sizes(
82 size_t rows, size_t cols, size_t nnz, lmmc_sparse_format_t format,
83 size_t* outer_ptr_bytes, size_t* idx_bytes, size_t* val_bytes) {
84 const size_t outer_size = (format == LMMC_SPARSE_CSR) ? rows : cols;
85 if (rows == 0 || cols == 0) {
87 }
88 if (format != LMMC_SPARSE_CSR && format != LMMC_SPARSE_CSC) {
90 }
91 if (outer_size == SIZE_MAX) {
93 }
94 if (!lmmc_safe_mul_size(outer_size + 1, sizeof(size_t), outer_ptr_bytes) ||
95 !lmmc_safe_mul_size(nnz, sizeof(size_t), idx_bytes) ||
96 !lmmc_safe_mul_size(nnz, sizeof(lmmc_real_t), val_bytes)) {
98 }
99 return LMMC_STATUS_OK;
100}
101
106static inline lmmc_status_t lmmc_sparse_create(size_t rows, size_t cols, size_t nnz, lmmc_sparse_format_t format, lmmc_sparse_mat_t* out_sparse) {
107 size_t outer_ptr_bytes = 0;
108 size_t idx_bytes = 0;
109 size_t val_bytes = 0;
110 size_t* outer_ptr = NULL;
111 size_t* inner_idx = NULL;
112 lmmc_real_t* values = NULL;
113
114 if (out_sparse == NULL) {
116 }
117 const lmmc_status_t status = lmmc_sparse_storage_sizes(
118 rows, cols, nnz, format, &outer_ptr_bytes, &idx_bytes, &val_bytes);
119 if (status != LMMC_STATUS_OK) {
120 return status;
121 }
122
123 outer_ptr = (size_t*)lmmc_memory_alloc(outer_ptr_bytes);
124 if (outer_ptr == NULL) {
126 }
127 memset(outer_ptr, 0, outer_ptr_bytes);
128
129 if (nnz > 0) {
130 inner_idx = (size_t*)lmmc_memory_alloc(idx_bytes);
131 values = (lmmc_real_t*)lmmc_memory_alloc(val_bytes);
132 if (inner_idx == NULL || values == NULL) {
133 if (inner_idx != NULL) {
134 lmmc_memory_free(inner_idx);
135 }
136 if (values != NULL) {
137 lmmc_memory_free(values);
138 }
139 lmmc_memory_free(outer_ptr);
141 }
142 memset(inner_idx, 0, idx_bytes);
143 memset(values, 0, val_bytes);
144 for (size_t i = 0; i < nnz; ++i) {
145 LMMC_REAL_INIT(&values[i]);
146 }
147 }
148
149 out_sparse->rows = rows;
150 out_sparse->cols = cols;
151 out_sparse->nnz = nnz;
152 out_sparse->row_ptr = outer_ptr;
153 out_sparse->col_idx = inner_idx;
154 out_sparse->values = values;
155 out_sparse->format = format;
156 out_sparse->owns_data = 1;
157 return LMMC_STATUS_OK;
158}
159#endif
LMMC binary real type and arithmetic spelling.
#define LMMC_REAL_INIT(x)
初始化一个 lmmc_real_t 变量(POD 类型为空操作)。
double lmmc_real_t
Public and internal LMMC real type.
LMMC 内部使用的公共工具(仅源文件可见).
void * lmmc_memory_alloc(size_t size)
void lmmc_memory_free(void *pointer)
Private recoverable allocator for persistent LMMC ownership.
lmmc_sparse_format_t
稀疏矩阵存储格式。
@ LMMC_SPARSE_CSR
@ LMMC_SPARSE_CSC
lmmc_sparse_format_t format
通用稀疏矩阵(CSR / CSC 共用同一结构)。
lmmc_status_t
LMMC 库统一返回的状态码.
@ LMMC_STATUS_OK
@ LMMC_STATUS_ALLOCATION_FAILED
@ LMMC_STATUS_INVALID_ARGUMENT