3#include <kids/core/kidsdata.h>
4#include <kids/sweep/fitter.h>
5#include <kids/timestream/solver.h>
6#include <kids/toltec/toltec.h>
7#include <kidscpp_config/gitversion.h>
9#include <tula/datatable.h>
22 using Solver = kids::TimeStreamSolver;
25 std::shared_ptr<spdlog::logger>
logger = spdlog::get(
"citlali_logger");
30 {
"weight_window_type", this->config().get_str(std::tuple{
31 "fitter",
"weight_window",
"type"})},
32 {
"weight_window_fwhm", this->config().get_typed<
double>(
33 std::tuple{
"fitter",
"weight_window",
"fwhm_Hz"})},
34 {
"modelspec", config.get_str(std::tuple{
"fitter",
"modelspec"})}}},
35 m_solver{Solver::Config{
36 {
"fitreportdir", this->config().get_str(std::tuple{
"solver",
"fitreportdir"})},
37 {
"exmode", this->config().get_str(std::tuple{
"solver",
"parallel_policy"})},
42 -> std::optional<std::string> {
44 std::shared_ptr<spdlog::logger> logger = spdlog::get(
"citlali_logger");
46 std::vector<std::string> missing_keys;
47 logger->debug(
"check kids data proc config\n{}", config);
48 if (!config.has(
"fitter")) {
49 missing_keys.push_back(
"fitter");
51 if (!config.has(
"solver")) {
52 missing_keys.push_back(
"solver");
54 if (missing_keys.empty()) {
57 return fmt::format(
"invalid or missing keys={}", missing_keys);
64 std::vector<kids::KidsData<>::meta_t> get_rawobs_meta(
const RawObs &);
67 auto populate_rtc_meta(
const RawObs &);
71 const tula::container_utils::Slice<int> &);
73 auto reduce_rawobs(
const RawObs &rawobs,
74 const tula::container_utils::Slice<int> &);
77 const tula::container_utils::Slice<int> &);
79 auto load_fit_report(
const RawObs &);
82 template <
typename Derived>
83 auto load_rawobs(
const RawObs &,
const Eigen::Index,
84 Eigen::DenseBase<Derived> &,
85 std::vector<Eigen::Index> &,
86 std::vector<Eigen::Index> &);
89 template <
typename loaded_t>
90 auto populate_rtc(loaded_t &,
const int,
const int,
94 template <
typename DerivedA,
typename DerivedB,
typename DerivedC>
95 auto load_rawobs_gaps(
const RawObs &,
const Eigen::Index,
96 Eigen::DenseBase<DerivedA>&,
97 std::vector<Eigen::Index>&,
98 Eigen::DenseBase<DerivedB>&,
99 std::vector<DerivedC>&,
103 template <
typename LoadedType,
typename DerivedA,
typename DerivedB,
typename DerivedC,
typename DerivedD>
104 auto populate_rtc_gaps(LoadedType &, Eigen::DenseBase<DerivedA>&,
105 std::vector<DerivedB>&,
106 std::vector<DerivedC>&,
107 const int,
const double,
108 Eigen::DenseBase<DerivedD>&,
109 const int,
const int,
const std::string);
118 template <
typename OStream>
120 return os << fmt::format(
"KidsDataProc(fitter={}, solver={})",
121 kidsproc.
fitter().config.pformat(),
122 kidsproc.
solver().config.pformat());
132 namespace kidsdata = predefs::kidsdata;
134 auto [kind, meta] = kidsdata::get_meta<>(source);
139 std::vector<kids::KidsData<>::meta_t> result;
140 for (
const auto &data_item : rawobs.
kidsdata()) {
147 std::vector<kids::KidsData<>::meta_t> result;
148 for (
const auto &data_item : rawobs.
kidsdata()) {
155 const tula::container_utils::Slice<int> &slice) {
156 logger->debug(
"kids reduce data_item {}", data_item);
158 namespace kidsdata = predefs::kidsdata;
160 auto [kind, meta] = kidsdata::get_meta<>(source);
161 if (!(kind & kids::KidsDataKind::TimeStream)) {
162 throw std::runtime_error(
163 fmt::format(
"wrong type of kids data {}", kind));
165 auto rts = kidsdata::read_data_slice<kids::KidsDataKind::RawTimeStream>(
167 auto result = this->
solver()(rts, Solver::Config{});
172 const tula::container_utils::Slice<int> &slice) {
173 logger->debug(
"kids reduce rawobs {}", rawobs);
174 std::vector<kids::TimeStreamSolverResult> result;
175 for (
const auto &data_item : rawobs.
kidsdata()) {
182 const tula::container_utils::Slice<int> &slice) {
183 logger->debug(
"kids reduce data_item {}", data_item);
185 namespace kidsdata = predefs::kidsdata;
187 auto [kind, meta] = kidsdata::get_meta<>(source);
188 if (!(kind & kids::KidsDataKind::TimeStream)) {
189 throw std::runtime_error(
190 fmt::format(
"wrong type of kids data {}", kind));
192 auto rts = kidsdata::read_data_slice<kids::KidsDataKind::RawTimeStream>(
198 std::vector<Eigen::MatrixXd> kids_models;
199 std::vector<std::string> header;
201 for (
const auto &data_item : rawobs.
kidsdata()) {
205 namespace fs = std::filesystem;
206 auto pattern = meta.get_str(
"cal_file");
207 std::string filepath{};
208 if (this->
solver().config.has(
"fitreportfile")) {
209 filepath = this->
solver().config.get_str(
"fitreportfile");
210 }
else if (this->
solver().config.has(
"fitreportdir")) {
211 auto dir = this->
solver().config.get_str(
"fitreportdir");
212 logger->info(
"look for fitreport dir {} with pattern {}", dir, pattern);
213 auto candidates = tula::filename_utils::find_regex(dir, pattern);
214 if (!candidates.empty()) {
215 filepath = candidates[0];
217 throw std::runtime_error(fmt::format(
218 "no fit report found in {} that matches {}", dir, pattern));
221 throw std::runtime_error(
222 fmt::format(
"no fit report location specified."));
224 logger->info(
"use fitreport file {}", filepath);
227 Eigen::MatrixXd table;
228 using meta_t = kids::KidsData<>::meta_t;
233 table = datatable::read<double, datatable::Format::ecsv>(
234 filepath, &header, &meta_);
236 tula::ecsv::meta_to_map<
typename meta_t::storage_t::key_type,
237 typename meta_t::storage_t::mapped_type>(
239 meta_cal = meta_t{std::move(meta_map)};
241 kids_models.push_back(std::move(table));
242 if (!meta_.IsNull()) {
243 logger->warn(
"un recongnized meta:\n{}", YAML::Dump(meta_));
245 }
catch (datatable::ParseError &e) {
246 logger->warn(
"unable to read fitreport file as ECSV {}: {}", filepath,
249 table = datatable::read<double, datatable::Format::ascii>(filepath,
251 kids_models.push_back(std::move(table));
253 }
catch (datatable::ParseError &e) {
254 logger->warn(
"unable to read fitreport file as ASCII {}: {}",
259 logger->info(
"meta_cal: {}", meta_cal.pformat());
260 logger->info(
"table {}",table);
261 logger->info(
"header {}",header);
268 return std::tuple{std::move(kids_models), std::move(header)};
271template <
typename Derived>
273 Eigen::DenseBase<Derived> &scan_indices,
274 std::vector<Eigen::Index> &start_indices,
275 std::vector<Eigen::Index> &end_indices) {
277 std::vector<kids::KidsData<kids::KidsDataKind::RawTimeStream>> result;
279 for (
const auto &data_item : rawobs.
kidsdata()) {
281 auto slice = tula::container_utils::Slice<int>{scan_indices(2,scan) + start_indices[i],
282 scan_indices(3,scan) + 1 + start_indices[i],
292template <
typename loaded_t>
294 const int n_pts,
const int n_det,
295 const std::string data_type) {
297 Eigen::MatrixXd data(n_pts, n_det);
301 for (std::vector<kids::KidsData<kids::KidsDataKind::RawTimeStream>>::
302 iterator it = loaded.begin(); it != loaded.end(); ++it) {
304 auto result = this->
solver()(*it, Solver::Config{});
306 Eigen::Index n_rows = result.data_out.xs.data.rows();
308 Eigen::Index n_cols = result.data_out.xs.data.cols();
311 if (data_type ==
"xs") {
312 data.block(0, i, n_rows, n_cols) = result.data_out.xs.data;
315 else if (data_type ==
"rs") {
316 data.block(0, i, n_rows, n_cols) = result.data_out.rs.data;
319 else if (data_type ==
"is") {
320 data.block(0, i, n_rows, n_cols) = result.data.is.data;
323 else if (data_type ==
"qs") {
324 data.block(0, i, n_rows, n_cols) = result.data.qs.data;
331 if ((data.array().isNaN()).any()) {
332 logger->error(
"nan found in data! Check that your KIDs data dir is correct.");
333 std::exit(EXIT_FAILURE);
336 if ((data.array().isInf()).any()) {
337 logger->error(
"inf found in data! Check that your KIDs data dir is correct.");
338 std::exit(EXIT_FAILURE);
344template <
typename DerivedA,
typename DerivedB,
typename DerivedC>
346 Eigen::DenseBase<DerivedA>& scan_indices,
347 std::vector<Eigen::Index>& start_indices,
348 Eigen::DenseBase<DerivedB>& t_common,
349 std::vector<DerivedC>& times,
352 std::vector<kids::KidsData<kids::KidsDataKind::RawTimeStream>> result;
354 double t0 = t_common(scan_indices(2, scan));
355 double t1 = t_common(scan_indices(3, scan));
358 for (
const auto &data_item : rawobs.
kidsdata()) {
359 Eigen::Index i_start = 0;
360 while (i_start < times[i].size()) {
361 double t = times[i](i_start);
371 Eigen::Index i_end = i_start;
372 while (i_end < times[i].size()) {
373 double t = times[i](i_end);
384 auto slice = tula::container_utils::Slice<int>{i_start, i_end + 1,
394template <
typename LoadedType,
typename DerivedA,
typename DerivedB,
typename DerivedC,
typename DerivedD>
396 std::vector<DerivedB>& times,
397 std::vector<DerivedC>& masks,
400 Eigen::DenseBase<DerivedD>& scan_indices,
401 const int n_pts,
const int n_det,
const std::string data_type) {
403 Eigen::MatrixXd data(n_pts, n_det);
405 double t0 = t_common(scan_indices(2, scan));
406 double t1 = t_common(scan_indices(3, scan));
408 Eigen::Index i = 0, j = 0;
410 for (std::vector<kids::KidsData<kids::KidsDataKind::RawTimeStream>>::
411 iterator it = loaded.begin(); it != loaded.end(); ++it) {
413 auto result = this->
solver()(*it, Solver::Config{});
415 Eigen::Index n_rows = result.data_out.xs.data.rows();
417 Eigen::Index n_cols = result.data_out.xs.data.cols();
419 Eigen::MatrixXd block(n_rows, n_cols);
422 if (data_type ==
"xs") {
423 block = result.data_out.xs.data;
424 }
else if (data_type ==
"rs") {
425 block = result.data_out.rs.data;
426 }
else if (data_type ==
"is") {
427 block = result.data.is.data;
428 }
else if (data_type ==
"qs") {
429 block = result.data.qs.data;
432 Eigen::Index i_start = 0;
433 while (i_start < times[j].size()) {
434 double t = times[j](i_start);
444 Eigen::Index i_end = i_start;
445 while (i_end < times[j].size()) {
446 double t = times[j](i_end);
457 masks[j].segment(scan_indices(2,scan), n_pts),
458 times[j].segment(i_start, i_end - i_start + 1),
461 data.block(0, i, n_pts, n_cols) = block;
468 if ((data.array().isNaN()).any()) {
469 logger->error(
"nan found in data! Check that your KIDs data dir is correct.");
470 std::exit(EXIT_FAILURE);
473 if ((data.array().isInf()).any()) {
474 logger->error(
"inf found in data! Check that your KIDs data dir is correct.");
475 std::exit(EXIT_FAILURE);
config::Config Config
Definition kids_main.cpp:17
bool extra_output
The KIDs data solver struct This wraps around the kids config.
Definition kidsproc.h:18
config::ConfigValidatorMixin< Derived, config::YamlConfig > ConfigMapper
Definition main_old.cpp:124
static Eigen::MatrixXd interp_data(const Eigen::VectorXd &t_common, const Eigen::VectorXi &mask, const Eigen::VectorXd &t_valid, const Eigen::MatrixXd &data_valid)
Definition utils.h:1218
Definition timestream.h:59
Solver & solver()
Definition kidsproc.h:113
auto reduce_rawobs(const RawObs &rawobs, const tula::container_utils::Slice< int > &)
Definition kidsproc.h:171
Solver m_solver
Definition kidsproc.h:128
const Solver & solver() const
Definition kidsproc.h:116
auto load_rawobs_gaps(const RawObs &, const Eigen::Index, Eigen::DenseBase< DerivedA > &, std::vector< Eigen::Index > &, Eigen::DenseBase< DerivedB > &, std::vector< DerivedC > &, const double)
Definition kidsproc.h:345
Fitter & fitter()
Definition kidsproc.h:112
static auto check_config(const config_t &config) -> std::optional< std::string >
Definition kidsproc.h:41
auto get_data_item_meta(const RawObs::DataItem &)
Definition kidsproc.h:131
auto load_fit_report(const RawObs &)
Definition kidsproc.h:197
auto populate_rtc_meta(const RawObs &)
Definition kidsproc.h:146
friend OStream & operator<<(OStream &os, const KidsDataProc &kidsproc)
Definition kidsproc.h:119
std::shared_ptr< spdlog::logger > logger
Definition kidsproc.h:25
kids::SweepFitter Fitter
Definition kidsproc.h:21
auto reduce_data_item(const RawObs::DataItem &, const tula::container_utils::Slice< int > &)
Definition kidsproc.h:154
ConfigMapper< KidsDataProc > Base
Definition kidsproc.h:20
std::vector< kids::KidsData<>::meta_t > get_rawobs_meta(const RawObs &)
Definition kidsproc.h:138
auto load_data_item(const RawObs::DataItem &, const tula::container_utils::Slice< int > &)
Definition kidsproc.h:181
auto load_rawobs(const RawObs &, const Eigen::Index, Eigen::DenseBase< Derived > &, std::vector< Eigen::Index > &, std::vector< Eigen::Index > &)
Definition kidsproc.h:272
KidsDataProc(config_t config)
Definition kidsproc.h:27
const Fitter & fitter() const
Definition kidsproc.h:115
auto populate_rtc(loaded_t &, const int, const int, const std::string)
Definition kidsproc.h:293
auto populate_rtc_gaps(LoadedType &, Eigen::DenseBase< DerivedA > &, std::vector< DerivedB > &, std::vector< DerivedC > &, const int, const double, Eigen::DenseBase< DerivedD > &, const int, const int, const std::string)
Definition kidsproc.h:395
kids::TimeStreamSolver Solver
Definition kidsproc.h:22
Fitter m_fitter
Definition kidsproc.h:127
The DataItem struct This represent a single data item that belongs to a particular observation.
Definition io.h:58
const std::string & filepath() const
Definition io.h:81
The raw obs struct This represents a single observation that contains a set of data items and calibra...
Definition io.h:50
auto kidsdata() const -> decltype(auto)
Definition io.h:283