Skip to content

Commit d293877

Browse files
authored
configurable print streams (#55)
1 parent e00e5c3 commit d293877

12 files changed

Lines changed: 432 additions & 51 deletions

File tree

.gitignore

Lines changed: 11 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,11 +3,20 @@ rust_wrapper/target
33
rust_wrapper/headers
44
rust_wrapper/Cargo.lock
55

6-
# CMake build directory
7-
build
6+
# CMake build directory and other cruft
7+
build/*
8+
*.cmake
9+
Makefile
10+
CmakeFiles/*
811

912
.*/
1013
!.vscode/
1114
!.github
1215

1316
CMakePresets.json
17+
18+
# compiled examples, but not source
19+
examples/cpp/*
20+
examples/c/*
21+
!examples/c/*.c
22+
!examples/cpp/*.cpp

examples/c/CMakeLists.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ set(C_EXAMPLES
1010
example_socp
1111
example_sdp
1212
example_json
13+
example_print_stream
1314
)
1415

1516
# Compile utils.c as a library

examples/c/example_json.c

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -19,14 +19,14 @@ int main(void)
1919
strcpy(filename, TO_STRING(EXAMPLES_ROOT_DIR));
2020
strcat(filename, "/data/hs35.json");
2121

22-
ClarabelDefaultSolver* solver = clarabel_DefaultSolver_read_from_file(filename);
22+
ClarabelDefaultSolver* solver = clarabel_DefaultSolver_load_from_file(filename);
2323
clarabel_DefaultSolver_solve(solver);
2424

2525
// write it back to a file
2626
// char filename_out[1024];
2727
// strcpy(filename_out, TO_STRING(EXAMPLES_ROOT_DIR));
2828
// strcat(filename_out, "/data/output_c.json");
29-
// clarabel_DefaultSolver_write_to_file(solver, filename_out);
29+
// clarabel_DefaultSolver_save_to_file(solver, filename_out);
3030

3131
clarabel_DefaultSolver_free(solver);
3232
return 0;

examples/c/example_print_stream.c

Lines changed: 75 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,75 @@
1+
// #define FEATURE_SDP
2+
#include "utils.h"
3+
#include <string.h>
4+
#include <Clarabel.h>
5+
#include <math.h>
6+
#include <stdio.h>
7+
8+
9+
int main(void)
10+
{
11+
12+
ClarabelCscMatrix P;
13+
clarabel_CscMatrix_init(
14+
&P,
15+
2, // row
16+
2, // col
17+
(uintptr_t[]){ 0, 1, 2 }, // colptr
18+
(uintptr_t[]){ 0, 1 }, // rowval
19+
(ClarabelFloat[]){ 6., 4. } // nzval
20+
);
21+
22+
ClarabelFloat q[2] = { -1., -4. };
23+
ClarabelCscMatrix A;
24+
clarabel_CscMatrix_init(
25+
&A,
26+
5, // row
27+
2, // col
28+
(uintptr_t[]){ 0, 3, 6 }, // colptr
29+
(uintptr_t[]){ 0, 1, 3, 0, 2, 4 }, // rowval
30+
(ClarabelFloat[]){ 1., 1., -1., -2., 1., -1. } // nzval
31+
);
32+
33+
ClarabelFloat b[5] = { 0., 1., 1., 1., 1. };
34+
35+
ClarabelSupportedConeT cones[2] = { ClarabelZeroConeT(1), ClarabelNonnegativeConeT(4) };
36+
37+
// Settings
38+
ClarabelDefaultSettings settings = clarabel_DefaultSettings_default();
39+
40+
// Build solver
41+
ClarabelDefaultSolver *solver = clarabel_DefaultSolver_new(
42+
&P, // P
43+
q, // q
44+
&A, // A
45+
b, // b
46+
2, // n_cones
47+
cones, &settings
48+
);
49+
50+
// redirect progress output to a file
51+
printf("Printing to file ....\n");
52+
clarabel_DefaultSolver_print_to_file(solver,"clarabel_example_print_stream.txt");
53+
54+
// solve
55+
clarabel_DefaultSolver_solve(solver);
56+
57+
// redirect progress output to a buffer
58+
printf("Printing to buffer ....\n");
59+
clarabel_DefaultSolver_print_to_buffer(solver);
60+
61+
// solve again
62+
clarabel_DefaultSolver_solve(solver);
63+
64+
// fetch and print the buffer
65+
printf("Recovering from buffer ....\n");
66+
const char* buffer = clarabel_DefaultSolver_get_print_buffer(solver);
67+
printf("%s\n", buffer);
68+
clarabel_free_print_buffer(buffer);
69+
70+
// restore the buffer to stdout
71+
printf("Printing to stdout ....\n");
72+
clarabel_DefaultSolver_print_to_stdout(solver);
73+
clarabel_DefaultSolver_solve(solver);
74+
75+
}

examples/cpp/CMakeLists.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@ set(CPP_EXAMPLES
99
example_sdp
1010
example_faer
1111
example_json
12+
example_print_stream
1213
)
1314

1415
# Define an executable target for each example

examples/cpp/example_json.cpp

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -23,13 +23,13 @@ int main(void)
2323
std::string filename = rootdir + filepath;
2424
std::cout << "Read from file: " << filename << endl;
2525

26-
DefaultSolver<double> solver = DefaultSolver<double>::read_from_file(filename);
26+
DefaultSolver<double> solver = DefaultSolver<double>::load_from_file(filename);
2727
solver.solve();
2828

2929
// write it back to a file
3030
// std::string outpath = "/data/output.json";
3131
// std::string filename_out = rootdir + outpath;
32-
// solver.write_to_file(filename_out);
32+
// solver.save_to_file(filename_out);
3333

3434
return 0;
3535

Lines changed: 73 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,73 @@
1+
#include "utils.h"
2+
3+
#include <Clarabel>
4+
#include <Eigen/Eigen>
5+
#include <vector>
6+
#include <iostream>
7+
8+
using namespace clarabel;
9+
using namespace std;
10+
using namespace Eigen;
11+
12+
int main(void)
13+
{
14+
/* From dense matrix:
15+
* [[6., 0.],
16+
* [0., 4.]]
17+
*/
18+
MatrixXd P_dense(2, 2);
19+
P_dense <<
20+
6., 0.,
21+
0., 4.;
22+
23+
SparseMatrix<double> P = P_dense.sparseView();
24+
P.makeCompressed();
25+
26+
Vector<double, 2> q = { -1., -4. };
27+
28+
MatrixXd A_dense(5, 2);
29+
A_dense <<
30+
1., -2., // <-- LHS of equality constraint (lower bound)
31+
1., 0., // <-- LHS of inequality constraint (upper bound)
32+
0., 1., // <-- LHS of inequality constraint (upper bound)
33+
-1., 0., // <-- LHS of inequality constraint (lower bound)
34+
0., -1.; // <-- LHS of inequality constraint (lower bound)
35+
36+
SparseMatrix<double> A = A_dense.sparseView();
37+
A.makeCompressed();
38+
39+
Vector<double, 5> b = { 0., 1., 1., 1., 1. };
40+
41+
vector<SupportedConeT<double>> cones
42+
{
43+
ZeroConeT<double>(1),
44+
NonnegativeConeT<double>(4),
45+
};
46+
47+
// Settings
48+
DefaultSettings<double> settings = DefaultSettings<double>::default_settings();
49+
50+
// Build solver
51+
DefaultSolver<double> solver(P, q, A, b, cones, settings);
52+
53+
// redirect progress output to a file
54+
std::cout << "Printing to file ...." << std::endl;
55+
solver.print_to_file("clarabel_example_print_stream.txt");
56+
solver.solve();
57+
58+
// redirect progress output to a buffer
59+
std::cout << "Printing to buffer ...." << std::endl;
60+
solver.print_to_buffer();
61+
solver.solve();
62+
63+
std::cout << "Recovering from buffer ...." << std::endl;
64+
std::string bufstr = solver.get_print_buffer();
65+
std::cout << bufstr << std::endl;
66+
67+
// restore the buffer to stdout
68+
std::cout << "Printing to stdout ...." << std::endl;
69+
solver.print_to_stdout();
70+
solver.solve();
71+
72+
return 0;
73+
}

include/c/DefaultSolver.h

Lines changed: 78 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -58,37 +58,101 @@ static inline ClarabelDefaultSolver *clarabel_DefaultSolver_new(const ClarabelCs
5858
}
5959

6060
#ifdef FEATURE_SERDE
61-
// DefaultSolver::read_from_file
62-
ClarabelDefaultSolver_f64 *clarabel_DefaultSolver_f64_read_from_file(const char *filename);
63-
ClarabelDefaultSolver_f32 *clarabel_DefaultSolver_f32_read_from_file(const char *filename);
61+
// DefaultSolver::load_from_file
62+
ClarabelDefaultSolver_f64 *clarabel_DefaultSolver_f64_load_from_file(const char *filename);
63+
ClarabelDefaultSolver_f32 *clarabel_DefaultSolver_f32_load_from_file(const char *filename);
6464
#ifdef CLARABEL_USE_FLOAT
65-
static inline ClarabelDefaultSolver *clarabel_DefaultSolver_read_from_file(const char *filename)
65+
static inline ClarabelDefaultSolver *clarabel_DefaultSolver_load_from_file(const char *filename)
6666
{
67-
return clarabel_DefaultSolver_f32_read_from_file(filename);
67+
return clarabel_DefaultSolver_f32_load_from_file(filename);
6868
}
6969
#else
70-
static inline ClarabelDefaultSolver *clarabel_DefaultSolver_read_from_file(const char *filename)
70+
static inline ClarabelDefaultSolver *clarabel_DefaultSolver_load_from_file(const char *filename)
7171
{
72-
return clarabel_DefaultSolver_f64_read_from_file(filename);
72+
return clarabel_DefaultSolver_f64_load_from_file(filename);
7373
}
7474
#endif // CLARABEL_USE_FLOAT
7575

76-
// DefaultSolver::write_to_file
77-
void clarabel_DefaultSolver_f64_write_to_file(ClarabelDefaultSolver_f64 *solver, const char *filename);
78-
void clarabel_DefaultSolver_f32_write_to_file(ClarabelDefaultSolver_f32 *solver, const char *filename);
76+
// DefaultSolver::save_to_file
77+
void clarabel_DefaultSolver_f64_save_to_file(ClarabelDefaultSolver_f64 *solver, const char *filename);
78+
void clarabel_DefaultSolver_f32_save_to_file(ClarabelDefaultSolver_f32 *solver, const char *filename);
7979
#ifdef CLARABEL_USE_FLOAT
80-
static inline void clarabel_DefaultSolver_write_to_file(ClarabelDefaultSolver *solver, const char *filename)
80+
static inline void clarabel_DefaultSolver_save_to_file(ClarabelDefaultSolver *solver, const char *filename)
8181
{
82-
clarabel_DefaultSolver_f32_write_to_file(solver,filename);
82+
clarabel_DefaultSolver_f32_save_to_file(solver,filename);
8383
}
8484
#else
85-
static inline void clarabel_DefaultSolver_write_to_file(ClarabelDefaultSolver *solver, const char *filename)
85+
static inline void clarabel_DefaultSolver_save_to_file(ClarabelDefaultSolver *solver, const char *filename)
8686
{
87-
clarabel_DefaultSolver_f64_write_to_file(solver,filename);
87+
clarabel_DefaultSolver_f64_save_to_file(solver,filename);
8888
}
8989
#endif // CLARABEL_USE_FLOAT
9090
#endif // FEATURE_SERDE
9191

92+
// DefaultSolver::print_to_stdout
93+
void clarabel_DefaultSolver_f64_print_to_stdout(ClarabelDefaultSolver_f64 *solver);
94+
void clarabel_DefaultSolver_f32_print_to_stdout(ClarabelDefaultSolver_f32 *solver);
95+
#ifdef CLARABEL_USE_FLOAT
96+
static inline void clarabel_DefaultSolver_print_to_stdout(ClarabelDefaultSolver *solver)
97+
{
98+
clarabel_DefaultSolver_f32_print_to_stdout(solver);
99+
}
100+
#else
101+
static inline void clarabel_DefaultSolver_print_to_stdout(ClarabelDefaultSolver *solver)
102+
{
103+
clarabel_DefaultSolver_f64_print_to_stdout(solver);
104+
}
105+
#endif // CLARABEL_USE_FLOAT
106+
107+
// DefaultSolver::print_to_file
108+
void clarabel_DefaultSolver_f64_print_to_file(ClarabelDefaultSolver_f64 *solver, const char *filename);
109+
void clarabel_DefaultSolver_f32_print_to_file(ClarabelDefaultSolver_f32 *solver, const char *filename);
110+
#ifdef CLARABEL_USE_FLOAT
111+
static inline void clarabel_DefaultSolver_print_to_file(ClarabelDefaultSolver *solver, const char *filename)
112+
{
113+
clarabel_DefaultSolver_f32_print_to_file(solver, const char *filename);
114+
}
115+
#else
116+
static inline void clarabel_DefaultSolver_print_to_file(ClarabelDefaultSolver *solver, const char *filename)
117+
{
118+
clarabel_DefaultSolver_f64_print_to_file(solver, filename);
119+
}
120+
#endif // CLARABEL_USE_FLOAT
121+
122+
// DefaultSolver::print_to_buffer
123+
void clarabel_DefaultSolver_f64_print_to_buffer(ClarabelDefaultSolver_f64 *solver);
124+
void clarabel_DefaultSolver_f32_print_to_buffer(ClarabelDefaultSolver_f32 *solver);
125+
#ifdef CLARABEL_USE_FLOAT
126+
static inline void clarabel_DefaultSolver_print_to_buffer(ClarabelDefaultSolver *solver)
127+
{
128+
clarabel_DefaultSolver_f32_print_to_buffer(solver);
129+
}
130+
#else
131+
static inline void clarabel_DefaultSolver_print_to_buffer(ClarabelDefaultSolver *solver)
132+
{
133+
clarabel_DefaultSolver_f64_print_to_buffer(solver);
134+
}
135+
#endif // CLARABEL_USE_FLOAT
136+
137+
// DefaultSolver::print_to_buffer
138+
// NB: The buffer is owned by rust and should not be freed by the C side caller.
139+
// Call clarabel_free_print_buffer to free the buffer. Failure to do so will
140+
// result in a memory leak.
141+
const char* clarabel_DefaultSolver_f64_get_print_buffer(ClarabelDefaultSolver_f64 *solver);
142+
const char* clarabel_DefaultSolver_f32_get_print_buffer(ClarabelDefaultSolver_f32 *solver);
143+
void clarabel_free_print_buffer(const char* buffer);
144+
145+
#ifdef CLARABEL_USE_FLOAT
146+
static inline const char* clarabel_DefaultSolver_get_print_buffer(ClarabelDefaultSolver *solver)
147+
{
148+
return clarabel_DefaultSolver_f32_get_print_buffer(solver);
149+
}
150+
#else
151+
static inline const char* clarabel_DefaultSolver_get_print_buffer(ClarabelDefaultSolver *solver)
152+
{
153+
return clarabel_DefaultSolver_f64_get_print_buffer(solver);
154+
}
155+
#endif // CLARABEL_USE_FLOAT
92156

93157

94158
// DefaultSolver::solve

include/cpp/DefaultInfo.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,7 @@ struct DefaultInfo
2828
T ktratio;
2929
double solve_time;
3030
clarabel::SolverStatus status;
31+
// NB : `PrintStream stream` not passed to C++ API
3132
};
3233

3334
// Instantiate the templates

0 commit comments

Comments
 (0)