dune-fem  2.4.1-rc
latextablewriter.hh
Go to the documentation of this file.
1 #ifndef DUNE_FEM_LATEXTABLEWRITER_HH
2 #define DUNE_FEM_LATEXTABLEWRITER_HH
3 
4 #include <cmath>
5 #include <fstream>
6 #include <limits>
7 #include <iomanip>
8 #include <sstream>
9 #include <vector>
10 #include <tuple>
11 
12 #include <dune/common/exceptions.hh>
13 #include <dune/common/tuples.hh>
14 
15 namespace Dune
16 {
17 
18  namespace Fem
19  {
20 
21  // NoDataException
22  // ---------------
23 
24  struct NoDataException {};
25 
26 
27 
28  // AbstractColumnWriter
29  // --------------------
30 
38  template< class DataTuple >
40  {
42  enum Alignment { AlignLeft, AlignCenter, AlignRight };
43 
45  virtual ~AbstractColumnWriter () {}
46 
48  virtual Alignment alignment () const { return AlignCenter; }
50  virtual std::string entry ( const DataTuple & ) const = 0;
52  virtual std::string header () const = 0;
53  };
54 
55 
56 
57  // TupleDataSource
58  // ---------------
59 
60  template< int N >
62  {
63  template< class DataTuple >
64  struct Value { typedef typename tuple_element< N, DataTuple >::type Type; };
65 
66  template< class DataTuple >
67  typename Value< DataTuple >::Type get ( const DataTuple &data ) const
68  throw ()
69  {
70  return std::get< N >( data );
71  }
72  };
73 
74 
75 
76  // ArrayDataSource
77  // ---------------
78 
79  template< class DataSource >
81  {
82  template< class DataTuple >
83  struct Value
84  {
85  typedef typename DataSource::template Value< DataTuple >::Type::value_type Type;
86  };
87 
88  ArrayDataSource ( const int index, const DataSource &source = DataSource() )
89  : index_( index ), source_( source )
90  {}
91 
92  template< class DataTuple >
93  typename Value< DataTuple >::Type get ( const DataTuple &data ) const
94  throw ()
95  {
96  return source_.get( data )[ index_ ];
97  }
98 
99  private:
100  int index_;
101  DataSource source_;
102  };
103 
104 
105 
106  // EOCDataSource
107  // -------------
108 
109  template< class WidthDataSource, class ErrorDataSource >
111  {
112  template< class DataTuple >
113  struct Value
114  {
115  typedef double Type;
116  };
117 
118  explicit EOCDataSource ( const WidthDataSource &widthSource = WidthDataSource(),
119  const ErrorDataSource &errorSource = ErrorDataSource() )
120  : widthSource_( widthSource ),
121  errorSource_( errorSource ),
122  hOld_( std::numeric_limits< double >::infinity() )
123  {}
124 
125  explicit EOCDataSource ( const ErrorDataSource &errorSource )
126  : errorSource_( errorSource ),
127  hOld_( std::numeric_limits< double >::infinity() )
128  {}
129 
130  template< class DataTuple >
131  typename Value< DataTuple >::Type get ( const DataTuple &data ) const
132  throw ( NoDataException )
133  {
134  double h = widthSource_.get( data );
135  double e = errorSource_.get( data );
136  std::swap( h, hOld_ );
137  std::swap( e, eOld_ );
138  if( h < std::numeric_limits< double >::infinity() )
139  return std::log( eOld_ / e ) / std::log( hOld_ / h );
140  else
141  throw( NoDataException() );
142  }
143 
144  private:
145  WidthDataSource widthSource_;
146  ErrorDataSource errorSource_;
147  mutable double hOld_;
148  mutable double eOld_;
149  };
150 
151 
152 
153  // NumberColumnWriter
154  // ------------------
155 
165  template< class DataTuple, class DataSource >
167  : public AbstractColumnWriter< DataTuple >
168  {
170 
171  public:
177  explicit NumberColumnWriter ( const std::string &header, const int decimals = 6,
178  const DataSource &source = DataSource() )
179  : header_( header ),
180  decimals_( decimals ),
181  source_( source )
182  {}
183 
189  NumberColumnWriter ( const std::string &header, const DataSource &source )
190  : header_( header ),
191  decimals_( 6 ),
192  source_( source )
193  {}
194 
196  typename BaseType::Alignment alignment () const
197  {
198  return BaseType::AlignRight;
199  }
200 
206  std::string entry ( const DataTuple &data ) const
207  throw (NoDataException)
208  {
209  return toString( source_.get( data ) );
210  }
211 
213  std::string header () const { return header_; }
214 
215  protected:
217  template< class Number >
218  std::string toString ( const Number &number ) const
219  {
220  std::ostringstream s;
221  s << std::fixed << std::setprecision( decimals_ );
222  s << "$" << number << "$";
223  return s.str();
224  }
225 
226  private:
227  std::string header_;
228  int decimals_;
229  DataSource source_;
230  };
231 
232 
233 
234  // LatexTableWriter
235  // ----------------
236 
243  template< class DataTuple >
245  {
249  typedef std::vector< const ColumnWriterType * > ColumnWriterVectorType;
250 
255  LatexTableWriter ( const std::string &filename, const ColumnWriterVectorType &columnWriter );
259  ~LatexTableWriter ();
260 
262  void writeRow ( const DataTuple &data );
264  void writeSeparator ();
265 
266  private:
268  typedef typename ColumnWriterVectorType::const_iterator ColumnWriterIteratorType;
269 
271  void cleanUp ();
272 
274  std::string preamble () const;
276  std::string header () const;
277 
278  ColumnWriterVectorType columnWriters_;
279  std::ofstream out_;
280  };
281 
282 
283 
284  // Implementation of LatexTableWriter
285  // ----------------------------------
286 
287  template< class DataTuple >
289  ::LatexTableWriter ( const std::string &filename, const ColumnWriterVectorType &columnWriters )
290  : columnWriters_( columnWriters ),
291  out_( filename.c_str() )
292  {
293  if( !out_ )
294  {
295  cleanUp();
296  DUNE_THROW( IOError, "Unable to open '" << filename << "'." );
297  }
298  out_ << "\\begin{tabular}{" << preamble() << "}" << std::endl;
299  writeSeparator();
300  out_ << header() << " \\\\"<< std::endl;
301  writeSeparator();
302  }
303 
304 
305  template< class DataTuple >
307  {
308  writeSeparator();
309  out_ << "\\end{tabular}" << std::endl;
310  cleanUp();
311  }
312 
313 
314  template< class DataTuple >
315  inline void LatexTableWriter< DataTuple >::writeRow ( const DataTuple &data )
316  {
317  std::string separator = "";
318  const ColumnWriterIteratorType end = columnWriters_.end();
319  for( ColumnWriterIteratorType it = columnWriters_.begin(); it != end; ++it )
320  {
321  out_ << separator;
322  separator = " & ";
323  if( *it )
324  {
325  try
326  {
327  out_ << (*it)->entry( data );
328  }
329  catch( const NoDataException & )
330  {
331  out_ << "\\multicolumn{1}{|c|}{---}";
332  }
333  }
334  }
335  out_ << " \\\\" << std::endl;
336  }
337 
338 
339  template< class DataTuple >
341  {
342  int b = 0, e = 0;
343 
344  const ColumnWriterIteratorType end = columnWriters_.end();
345  for( ColumnWriterIteratorType it = columnWriters_.begin(); it != end; ++it, ++e )
346  {
347  if( !(*it) )
348  {
349  if( b < e )
350  out_ << "\\cline{" << (b+1) << "-" << e << "}";
351  b = e+1;
352  }
353  }
354  if( b < e )
355  out_ << "\\cline{" << (b+1) << "-" << e << "}";
356  out_ << std::endl;
357  }
358 
359 
360  template< class DataTuple >
362  {
363  const ColumnWriterIteratorType end = columnWriters_.end();
364  for( ColumnWriterIteratorType it = columnWriters_.begin(); it != end; ++it )
365  {
366  if( *it )
367  delete( *it );
368  }
369  }
370 
371 
372  template< class DataTuple >
373  inline std::string LatexTableWriter< DataTuple >::header () const
374  {
375  std::string header, separator;
376  const ColumnWriterIteratorType end = columnWriters_.end();
377  for( ColumnWriterIteratorType it = columnWriters_.begin(); it != end; ++it )
378  {
379  header += separator;
380  separator = " & ";
381  if( *it )
382  header += "\\multicolumn{1}{|c|}{" + (*it)->header() + "}";
383  }
384  return header;
385  }
386 
387 
388  template< class DataTuple >
389  inline std::string LatexTableWriter< DataTuple >::preamble () const
390  {
391  const char alignment[] = { 'l', 'c', 'r' };
392 
393  std::string preamble( "|" );
394  const ColumnWriterIteratorType end = columnWriters_.end();
395  for( ColumnWriterIteratorType it = columnWriters_.begin(); it != end; ++it )
396  {
397  if( *it )
398  preamble += alignment[ (*it)->alignment() ];
399  else
400  preamble += "@{}p{0.2em}@{}";
401  preamble += "|";
402  }
403  return preamble;
404  }
405 
406  } // namespace Fem
407 
408 } // namespace Dune
409 
410 #endif // #ifndef DUNE_FEM_LATEXTABLEWRITER_HH
~LatexTableWriter()
writes "\end{tabular}" to the latex file and removes column vector
Definition: latextablewriter.hh:306
BaseType::Alignment alignment() const
set the aligment of the entries for this column in the latex table
Definition: latextablewriter.hh:196
Definition: latextablewriter.hh:83
EOCDataSource(const WidthDataSource &widthSource=WidthDataSource(), const ErrorDataSource &errorSource=ErrorDataSource())
Definition: latextablewriter.hh:118
virtual ~AbstractColumnWriter()
Destructor.
Definition: latextablewriter.hh:45
EOCDataSource(const ErrorDataSource &errorSource)
Definition: latextablewriter.hh:125
virtual Alignment alignment() const
Definition: latextablewriter.hh:48
gets the N th element of a provided tuple assuming its a number
Definition: latextablewriter.hh:166
NumberColumnWriter(const std::string &header, const DataSource &source)
Constructor of NumberColumnWriter where decimal default to 6.
Definition: latextablewriter.hh:189
Definition: latextablewriter.hh:61
static double log(const Double &v)
Definition: double.hh:865
Class representing column writer in general.
Definition: latextablewriter.hh:39
writes latex tables based on user-defined row structure
Definition: latextablewriter.hh:244
Definition: coordinate.hh:4
std::vector< const ColumnWriterType * > ColumnWriterVectorType
Abstract column vector type.
Definition: latextablewriter.hh:249
Definition: latextablewriter.hh:110
DataSource::template Value< DataTuple >::Type::value_type Type
Definition: latextablewriter.hh:85
ArrayDataSource(const int index, const DataSource &source=DataSource())
Definition: latextablewriter.hh:88
std::string toString(const Number &number) const
converts number to std::string
Definition: latextablewriter.hh:218
Alignment
The alignment for the data in this column.
Definition: latextablewriter.hh:42
Definition: latextablewriter.hh:80
STL namespace.
void writeSeparator()
Adds extra space between two columns in the latex table.
Definition: latextablewriter.hh:340
Definition: latextablewriter.hh:64
NumberColumnWriter(const std::string &header, const int decimals=6, const DataSource &source=DataSource())
Definition: latextablewriter.hh:177
Definition: latextablewriter.hh:113
Definition: latextablewriter.hh:24
double Type
Definition: latextablewriter.hh:115
AbstractColumnWriter< DataTuple > ColumnWriterType
Abstract column type.
Definition: latextablewriter.hh:247
LatexTableWriter(const std::string &filename, const ColumnWriterVectorType &columnWriter)
Definition: latextablewriter.hh:289
std::string entry(const DataTuple &data) const
returns N the element from data tuple
Definition: latextablewriter.hh:206
void writeRow(const DataTuple &data)
Write row to the table.
Definition: latextablewriter.hh:315
std::string header() const
return Column titles in latex row format
Definition: latextablewriter.hh:213
tuple_element< N, DataTuple >::type Type
Definition: latextablewriter.hh:64