MARLEY (Model of Argon Reaction Low Energy Yields)  v1.2.0
A Monte Carlo event generator for tens-of-MeV neutrino interactions
Logger.hh
1 //
5 // This file is part of MARLEY (Model of Argon Reaction Low Energy Yields)
6 //
7 // MARLEY is free software: you can redistribute it and/or modify it under the
8 // terms of version 3 of the GNU General Public License as published by the
9 // Free Software Foundation.
10 //
11 // For the full text of the license please see COPYING or
12 // visit http://opensource.org/licenses/GPL-3.0
13 //
14 // Please respect the MCnet academic usage guidelines. See GUIDELINES
15 // or visit https://www.montecarlonet.org/GUIDELINES for details.
16 
17 #pragma once
18 #include <algorithm>
19 #include <fstream>
20 #include <memory>
21 #include <sstream>
22 #include <vector>
23 
24 // Forward declare some MARLEY classes and their operator<< functions so that
25 // we can stream them to the Logger
26 namespace marley {
27  class HauserFeshbachDecay;
28  class Parity;
29  class Target;
30  class TargetAtom;
31 }
32 
33 std::ostream& operator<<(std::ostream& out,
34  const marley::HauserFeshbachDecay& hfd);
35 
36 std::ostream& operator<<(std::ostream& out, const marley::Parity& p);
37 std::ostream& operator<<(std::ostream& out, const marley::Target& t);
38 std::ostream& operator<<(std::ostream& out, const marley::TargetAtom& ta);
39 
40 namespace marley {
41 
45  class Logger {
46 
47  public:
48 
54  enum class LogLevel { DISABLED, ERROR, WARNING, INFO, DEBUG };
55 
56  private:
57 
60  const char* loglevel_to_str(LogLevel lev);
61 
63  class OutStream {
64 
65  friend class Logger;
66  friend class OutStreamVector;
67 
68  public:
69 
88  OutStream(std::shared_ptr<std::ostream> os, LogLevel lev,
89  bool enable = true);
90 
105  OutStream(std::ostream& os, LogLevel lev, bool enable = true);
106 
107  private:
108 
111  std::shared_ptr<std::ostream> stream_;
112 
114  LogLevel level_;
115 
118  bool enabled_;
119  };
120 
123  class OutStreamVector : public std::vector<OutStream> {
124  public:
125 
126  OutStreamVector() : std::vector<OutStream>() {}
127 
128  template<typename OutputType> OutStreamVector&
129  operator<<(const OutputType& ot);
130 
135  OutStreamVector& operator<<(std::ostream& (*manip)(std::ostream&));
136 
138  OutStreamVector& operator<<(std::ios_base& (*manip)(std::ios_base&));
139  };
140 
144  class Message {
145  public:
146  Message(OutStreamVector& vec) : osvec_( vec ) {}
147 
148  inline ~Message() {
149  osvec_ << '\n';
150  }
151 
152  template<typename OutputType> Message&&
153  operator<<(const OutputType& ot)
154  {
155  osvec_ << ot;
156  return std::move( *this );
157  }
158 
159  protected:
160  OutStreamVector& osvec_;
161  };
162 
166  Logger(bool log_enabled = true);
167 
168  public:
169 
171  static Logger& Instance();
172 
181  void add_stream(std::shared_ptr<std::ostream> stream,
182  LogLevel level = LogLevel::WARNING);
183 
190  void add_stream(std::ostream& stream,
191  LogLevel level = LogLevel::WARNING);
192 
194  void clear_streams();
195 
198  void enable(bool log_enabled = true);
199 
201  inline void disable();
202 
204  void flush();
205 
208  void newline();
209 
212  bool has_stream(const std::ostream& stream) const;
213 
217  Message log(LogLevel lev = LogLevel::WARNING);
218 
219  // Make the singleton Logger uncopyable and unmovable
221  Logger(const Logger&) = delete;
223  Logger& operator=(const Logger&) = delete;
225  Logger(Logger&&) = delete;
227  Logger& operator=(Logger&&) = delete;
228 
229  private:
230 
241  OutStream* find_stream(const std::ostream* os, bool& stream_enabled,
242  LogLevel level);
243 
244  // @brief Returns a pointer to the given stream's OutStream object if
245  // it has been added to the Logger, or nullptr otherwise.
246  const OutStream* get_stream(const std::ostream* os) const;
247 
248  // @brief Returns a pointer to the given stream's OutStream object if
249  // it has been added to the Logger, or nullptr otherwise.
250  OutStream* get_stream(const std::ostream* os);
251 
254  OutStreamVector streams_;
255 
257  bool enabled_;
258 
260  LogLevel old_level_;
261  };
262 
263 }
264 
265 // Inline function definitions
266 inline void marley::Logger::disable() { enable(false); }
267 
268 template<typename OutputType> marley::Logger::OutStreamVector&
269  marley::Logger::OutStreamVector::operator<<(const OutputType& ot)
270 {
271  for (auto s : *this) if (s.enabled_ && s.stream_) *(s.stream_) << ot;
272  return *this;
273 }
274 
275 // Convenient shortcut functions for recording log messages
276 inline auto MARLEY_LOG_ERROR() {
277  return marley::Logger::Instance().log(marley::Logger::LogLevel::ERROR);
278 }
279 
280 inline auto MARLEY_LOG_WARNING() {
281  return marley::Logger::Instance().log(marley::Logger::LogLevel::WARNING);
282 }
283 
284 inline auto MARLEY_LOG_INFO() {
285  return marley::Logger::Instance().log(marley::Logger::LogLevel::INFO);
286 }
287 
288 inline auto MARLEY_LOG_DEBUG() {
289  return marley::Logger::Instance().log(marley::Logger::LogLevel::DEBUG);
290 }
Monte Carlo implementation of the Hauser-Feshbach statistical model for decays of highly-excited nucl...
Definition: HauserFeshbachDecay.hh:31
Simple singleton logging class.
Definition: Logger.hh:45
static Logger & Instance()
Get the singleton instance of the Logger class.
Definition: Logger.cc:109
Logger(const Logger &)=delete
Deleted copy constructor.
Logger & operator=(Logger &&)=delete
Deleted move assignment operator.
Message log(LogLevel lev=LogLevel::WARNING)
Prepare the Logger to receive a log message via the << stream operator.
Definition: Logger.cc:182
LogLevel
Defines the logging levels recognized by the marley::Logger.
Definition: Logger.hh:54
Logger & operator=(const Logger &)=delete
Deleted copy assignment operator.
void clear_streams()
Clear the vector of streams that receive Logger output.
Definition: Logger.cc:87
void disable()
Disable the Logger.
Definition: Logger.hh:266
void add_stream(std::shared_ptr< std::ostream > stream, LogLevel level=LogLevel::WARNING)
Add a std::ostream to the vector of streams that will receive Logger output.
Definition: Logger.cc:158
void enable(bool log_enabled=true)
Enable or disable the Logger.
Definition: Logger.cc:177
void newline()
Send a newline character to all output streams ignoring logging level settings.
Definition: Logger.cc:83
void flush()
Flush all output streams associated with the Logger.
Definition: Logger.cc:79
bool has_stream(const std::ostream &stream) const
Returns true if stream is already registered with the Logger, or false otherwise.
Definition: Logger.cc:114
Logger(Logger &&)=delete
Deleted move constructor.
Type-safe representation of a parity value (either +1 or -1)
Definition: Parity.hh:25
An atomic target for a lepton scattering reaction.
Definition: TargetAtom.hh:26
Description of a macroscopic target for scattering reactions.
Definition: Target.hh:32