PISM, A Parallel Ice Sheet Model 2.3.0-79cae578d committed by Constantine Khrulev on 2026-03-22
Loading...
Searching...
No Matches
NetCDFConfig.cc
Go to the documentation of this file.
1/* Copyright (C) 2014, 2015, 2016, 2017, 2019, 2021, 2023, 2024, 2025 PISM Authors
2 *
3 * This file is part of PISM.
4 *
5 * PISM is free software; you can redistribute it and/or modify it under the
6 * terms of the GNU General Public License as published by the Free Software
7 * Foundation; either version 3 of the License, or (at your option) any later
8 * version.
9 *
10 * PISM is distributed in the hope that it will be useful, but WITHOUT ANY
11 * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
12 * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more
13 * details.
14 *
15 * You should have received a copy of the GNU General Public License
16 * along with PISM; if not, write to the Free Software
17 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
18 */
19#include <vector>
20
21#include "pism/util/NetCDFConfig.hh"
22#include "VariableMetadata.hh"
23#include "pism/util/io/IO_Flags.hh"
24#include "pism/util/error_handling.hh"
25#include "pism/util/io/File.hh"
26#include "pism/util/io/OutputWriter.hh"
27#include "pism/util/io/io_helpers.hh"
28
29namespace pism {
30
31NetCDFConfig::NetCDFConfig(const std::string &name, units::System::Ptr system)
32 : Config(system),
33 m_data(name, system) {
34}
35
38
39bool NetCDFConfig::is_set_impl(const std::string &name) const {
40 return m_data.has_attribute(name);
41}
42
43// doubles
44
45double NetCDFConfig::get_number_impl(const std::string &name) const {
46 const auto &doubles = m_data.all_doubles();
47 if (doubles.find(name) != doubles.end()) {
48 return m_data.get_number(name);
49 }
50
52 "numeric parameter '%s' was not set. (Parameters read from '%s'.)",
53 name.c_str(), m_config_filename.c_str());
54
55 return 0; // can't happen
56}
57
58std::vector<double> NetCDFConfig::get_numbers_impl(const std::string &name) const {
59 const auto& doubles = m_data.all_doubles();
60 if (doubles.find(name) != doubles.end()) {
61 return m_data.get_numbers(name);
62 }
63
65 "numeric parameter '%s' was not set. (Parameters read from '%s'.)",
66 name.c_str(), m_config_filename.c_str());
67
68 return {}; // can't happen
69}
70
72 Doubles result;
73
74 for (const auto& d : m_data.all_doubles()) {
75 result[d.first] = d.second;
76 }
77 return result;
78}
79
80
81void NetCDFConfig::set_number_impl(const std::string &name, double value) {
82 m_data.set_number(name, value);
83}
84
85void NetCDFConfig::set_numbers_impl(const std::string &name,
86 const std::vector<double> &values) {
87 m_data.set_numbers(name, values);
88}
89
90// strings
91
92std::string NetCDFConfig::get_string_impl(const std::string &name) const {
93 const auto& strings = m_data.all_strings();
94 if (strings.find(name) != strings.end()) {
95 return m_data[name];
96 }
97
99 "string parameter '%s' was not set. (Read from '%s'.)\n", name.c_str(),
100 m_config_filename.c_str());
101
102 return std::string(); // will never happen
103}
104
106 auto strings = m_data.all_strings();
107 Strings result;
108
109 for (const auto& s : strings) {
110 std::string name = s.first;
111 std::string value = s.second;
112
113 auto k = strings.find(name + "_type");
114 if (k != strings.end() and k->second == "flag") {
115 // Flags are stored as strings. Skip them.
116 continue;
117 }
118
119 result[name] = value;
120 }
121 return result;
122}
123
124void NetCDFConfig::set_string_impl(const std::string &name, const std::string &value) {
125 m_data[name] = value;
126}
127
128// flags
129
130static bool string_is_false(const std::string &value) {
131 return value == "false" or value == "off" or value == "no";
132}
133
134static bool string_is_true(const std::string &value) {
135 return value == "true" or value == "on" or value == "yes";
136}
137
138bool NetCDFConfig::get_flag_impl(const std::string &name) const {
139 const auto &strings = m_data.all_strings();
140 auto j = strings.find(name);
141 if (j != strings.end()) {
142
143 const std::string &value = j->second;
144
145 if (string_is_false(value)) {
146 return false;
147 }
148
149 if (string_is_true(value)) {
150 return true;
151 }
152
153 throw RuntimeError::formatted(PISM_ERROR_LOCATION, "Parameter '%s' (%s) cannot be interpreted as a flag.\n"
154 "Please make sure that it is set to one of 'true', 'yes', 'on', 'false', 'no', 'off'.",
155 name.c_str(), value.c_str());
156 }
157
158 throw RuntimeError::formatted(PISM_ERROR_LOCATION, "Parameter '%s' was not set. (Read from '%s'.)",
159 name.c_str(), m_config_filename.c_str());
160
161 return true; // will never happen
162}
163
165 Flags result;
166
167 for (const auto& b : m_data.all_strings()) {
168 std::string name = b.first;
169 std::string value = b.second;
170
171 if (string_is_true(value)) {
172 result[name] = true;
173 } else if (string_is_false(value)) {
174 result[name] = false;
175 }
176 }
177 return result;
178}
179
180//! Set a value of a flag flag.
181void NetCDFConfig::set_flag_impl(const std::string &name, bool value) {
182 m_data[name] = value ? "true" : "false";
183}
184
185// file I/O
186
187//! Read flag flags and double parameters from a NetCDF file.
188/*!
189 Erases all the present parameters before reading.
190*/
191void NetCDFConfig::read_impl(const File &file) {
192
194
195 m_config_filename = file.name();
196}
197
198} // end of namespace pism
std::map< std::string, std::string > Strings
Definition Config.hh:111
std::map< std::string, std::vector< double > > Doubles
Definition Config.hh:96
std::map< std::string, bool > Flags
Definition Config.hh:118
A class for storing and accessing PISM configuration flags and parameters.
Definition Config.hh:56
std::string name() const
Definition File.cc:274
High-level PISM I/O class.
Definition File.hh:57
bool get_flag_impl(const std::string &name) const
void set_numbers_impl(const std::string &name, const std::vector< double > &values)
bool is_set_impl(const std::string &name) const
VariableMetadata m_data
Doubles all_doubles_impl() const
void set_number_impl(const std::string &name, double value)
void set_flag_impl(const std::string &name, bool value)
Set a value of a flag flag.
void read_impl(const File &file)
Read flag flags and double parameters from a NetCDF file.
std::string get_string_impl(const std::string &name) const
double get_number_impl(const std::string &name) const
NetCDFConfig(const std::string &name, units::System::Ptr unit_system)
void set_string_impl(const std::string &name, const std::string &value)
Strings all_strings_impl() const
Flags all_flags_impl() const
std::vector< double > get_numbers_impl(const std::string &name) const
std::string m_config_filename
the name of the file this config database was initialized from
static RuntimeError formatted(const ErrorLocation &location, const char format[],...) __attribute__((format(printf
build a RuntimeError with a formatted message
VariableMetadata & set_number(const std::string &name, double value)
Set a scalar attribute to a single (scalar) value.
double get_number(const std::string &name) const
Get a single-valued scalar attribute.
const std::map< std::string, std::string > & all_strings() const
std::shared_ptr< units::System > unit_system() const
std::vector< double > get_numbers(const std::string &name) const
Get an array-of-doubles attribute.
bool has_attribute(const std::string &name) const
VariableMetadata & set_numbers(const std::string &name, const std::vector< double > &values)
Set a scalar attribute to a single (scalar) value.
std::string get_name() const
const std::map< std::string, std::vector< double > > & all_doubles() const
std::shared_ptr< System > Ptr
Definition Units.hh:47
#define PISM_ERROR_LOCATION
VariableMetadata read_attributes(const File &file, const std::string &variable_name, std::shared_ptr< units::System > unit_system)
static bool string_is_false(const std::string &value)
static const double k
Definition exactTestP.cc:42
static bool string_is_true(const std::string &value)