Chi-Tech
PostProcessorPrinter_00b_history.cc
Go to the documentation of this file.
2
4
6
7#include "chi_runtime.h"
8#include "chi_log.h"
9
10namespace chi
11{
12
13// ##################################################################
15 const std::string& pps_typename,
16 const std::vector<const PostProcessor*>& pp_list,
17 const Event& event,
18 bool per_column_sizes /*=false*/) const
19{
20 if (pp_list.empty()) return;
21 //======================================== Establish unique time history sizes
22 std::set<size_t> unq_time_histsizes;
23
24 for (const auto& pp : pp_list)
25 {
26 const size_t time_histsize = pp->GetTimeHistory().size();
27 unq_time_histsizes.insert(time_histsize);
28 }
29
30 //======================================== Subscribe pps to unique time
31 // hist sizes
32 std::map<size_t, std::vector<const PostProcessor*>> pp_timehist_size_subs;
33 for (size_t time_histsize : unq_time_histsizes)
34 {
35 auto& subs = pp_timehist_size_subs[time_histsize];
36 for (const auto& pp : pp_list)
37 if (pp->GetTimeHistory().size() == time_histsize) subs.push_back(pp);
38 }
39
40 //======================================== For each timeline. Build the table
41 for (const auto& [timehistsize, pp_sub_list] : pp_timehist_size_subs)
42 {
43 if (pp_sub_list.empty()) continue;
44
45 //+2 top header + bottom header
46 const size_t num_rows =
47 std::min(size_t(time_history_limit_ + 2), timehistsize + 2);
48 const size_t num_cols = pp_sub_list.size() + 1; //+1 time column
49
50 auto value_matrix =
51 BuildPPHistoryMatrix(timehistsize, time_history_limit_, pp_sub_list);
52
53 // Find largest column
54 size_t max_column_width = 0;
55 for (const auto& row : value_matrix)
56 for (const auto& entry : row)
57 max_column_width = std::max(max_column_width, entry.size());
58 max_column_width =
59 std::max(max_column_width, size_t(15)); // minimum size 15
60
61 std::vector<size_t> col_sizes;
62 if (not per_column_sizes) col_sizes.assign(num_cols, max_column_width);
63 else
64 {
65 col_sizes.assign(num_cols, 0);
66 for (size_t j = 0; j < num_cols; ++j)
67 {
68 col_sizes[j] = value_matrix[0][j].size();
69 for (size_t t = 1; t < num_rows; ++t)
70 col_sizes[j] = std::max(col_sizes[j], value_matrix[t][j].size());
71 }
72 }
73
74 /**Lambda to left pad an entry.*/
75 auto LeftPad = [](std::string& entry, size_t width)
76 {
77 const size_t pad_size = width - entry.size();
78 entry = std::string(pad_size, ' ').append(entry);
79 };
80 /**Lambda to right pad an entry.*/
81 auto RightPad = [](std::string& entry, size_t width)
82 {
83 const size_t pad_size = width - entry.size();
84 entry.append(std::string(pad_size, ' '));
85 };
86
87 for (size_t j = 0; j < num_cols; ++j)
88 RightPad(value_matrix[0][j], col_sizes[j]);
89 for (size_t i = 1; i < num_rows; ++i)
90 for (size_t j = 0; j < num_cols; ++j)
91 LeftPad(value_matrix[i][j], col_sizes[j]);
92
93 // Build sub matrix structure
94 std::vector<size_t> sub_mat_sizes;
95 size_t total_width = 0;
96 size_t col_counter = 0;
97 for (size_t c = 0; c < num_cols; ++c)
98 {
99 //[0] | 0.000000 | 1.000000 | 0.000000e+00 |
100 // 5 chars for log, 2 for '| ', 1 for ' ', 2 for ' |' at end
101 const size_t projected_total_width =
102 total_width + col_sizes[c] + 5 + 2 + 1 + 2;
103 if (projected_total_width > table_column_limit_)
104 {
105 total_width = col_sizes[c] + 5 + 2 + 1; // the time column
106 sub_mat_sizes.push_back(col_counter);
107 }
108 col_counter += 1;
109 total_width += col_sizes[c] + 2 + 1;
110 }
111 sub_mat_sizes.push_back(col_counter);
112
113 // Now actually build the sub-matrices
114 typedef std::vector<std::string> VecStr;
115 typedef std::vector<VecStr> MatStr;
116 std::vector<MatStr> sub_matrices;
117 size_t last_k = 1;
118 for (const size_t k : sub_mat_sizes)
119 {
120 MatStr sub_matrix(num_rows, VecStr(k - last_k + 1, ""));
121 // Copy time col
122 for (size_t i = 0; i < num_rows; ++i)
123 sub_matrix[i][0] = value_matrix[i][0];
124
125 // Copy other
126 for (size_t i = 0; i < num_rows; ++i)
127 {
128 size_t j_star = 1;
129 for (size_t j = last_k; j < k; ++j, ++j_star)
130 sub_matrix[i][j_star] = value_matrix[i][j];
131 }
132 last_k = k;
133 sub_matrices.push_back(std::move(sub_matrix));
134 }
135
136 std::stringstream outstr;
137 for (const auto& sub_matrix : sub_matrices)
138 outstr << PrintPPsSubTimeHistory(sub_matrix);
139
140 Chi::log.Log() << "\n"
141 << pps_typename << " post-processors history at event \""
142 << event.Name() << "\"\n"
143 << outstr.str();
144 } // for each thing in pp_timehist_size_subs
145}
146
148 const std::vector<std::vector<std::string>>& sub_history)
149{
150 const size_t num_rows = sub_history.size();
151 const size_t num_cols = sub_history.front().size();
152
153 std::stringstream output;
154 std::stringstream hline;
155 for (size_t k = 0; k < num_cols; ++k)
156 {
157 const size_t col_str_size = sub_history.front()[k].size();
158 hline << "*" << std::string(col_str_size + 2, '-');
159 }
160 hline << "*\n";
161
162 output << hline.str();
163 for (size_t i = 0; i < num_rows; ++i)
164 {
165 if (i == 1) output << hline.str();
166 std::stringstream line;
167 for (size_t k = 0; k < num_cols; ++k)
168 line << "| " << sub_history[i][k] << " ";
169 line << "|\n";
170 output << line.str();
171 if (i == (num_rows - 1)) output << hline.str();
172 }
173
174 return output.str();
175}
176
177} // namespace chi
static chi::ChiLog & log
Definition: chi_runtime.h:81
LogStream Log(LOG_LVL level=LOG_0)
Definition: chi_log.cc:35
static std::vector< std::vector< std::string > > BuildPPHistoryMatrix(size_t timehistsize, size_t time_history_limit, const std::vector< const PostProcessor * > &pp_sub_list)
void PrintPPsTimeHistory(const std::string &pps_typename, const std::vector< const PostProcessor * > &pp_list, const Event &event, bool per_column_sizes=false) const
size_t time_history_limit_
size_t table_column_limit_
static std::string PrintPPsSubTimeHistory(const std::vector< std::vector< std::string > > &sub_history)