CompactIOList.C
Go to the documentation of this file.
1 /*---------------------------------------------------------------------------*\
2  ========= |
3  \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
4  \\ / O peration |
5  \\ / A nd | www.openfoam.com
6  \\/ M anipulation |
7 -------------------------------------------------------------------------------
8  Copyright (C) 2011-2017 OpenFOAM Foundation
9  Copyright (C) 2015-2022 OpenCFD Ltd.
10 -------------------------------------------------------------------------------
11 License
12  This file is part of OpenFOAM.
13 
14  OpenFOAM is free software: you can redistribute it and/or modify it
15  under the terms of the GNU General Public License as published by
16  the Free Software Foundation, either version 3 of the License, or
17  (at your option) any later version.
18 
19  OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
20  ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
21  FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
22  for more details.
23 
24  You should have received a copy of the GNU General Public License
25  along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
26 
27 \*---------------------------------------------------------------------------*/
28 
29 #include "CompactIOList.H"
30 #include "labelList.H"
31 
32 // * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
33 
34 template<class T, class BaseType>
36 {
37  Istream& is = readStream(word::null);
38 
39  if (headerClassName() == IOList<T>::typeName)
40  {
41  is >> static_cast<List<T>&>(*this);
42  close();
43  }
44  else if (headerClassName() == typeName)
45  {
46  is >> *this;
47  close();
48  }
49  else
50  {
52  << "unexpected class name " << headerClassName()
53  << " expected " << typeName
54  << " or " << IOList<T>::typeName << endl
55  << " while reading object " << name()
56  << exit(FatalIOError);
57  }
58 }
59 
60 
61 template<class T, class BaseType>
63 {
64  if
65  (
66  readOpt() == IOobject::MUST_READ
67  || (isReadOptional() && headerOk())
68  )
69  {
70  readFromStream();
71  return true;
72  }
73 
74  return false;
75 }
76 
77 
78 template<class T, class BaseType>
80 {
81  label size = 0;
82  forAll(*this, i)
83  {
84  const label oldSize = size;
85  size += this->operator[](i).size();
86  if (size < oldSize)
87  {
88  return true;
89  }
90  }
91  return false;
92 }
93 
94 
95 // * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * * //
96 
97 template<class T, class BaseType>
99 :
100  regIOobject(io)
101 {
102  readContents();
103 }
104 
105 
106 template<class T, class BaseType>
108 (
109  const IOobject& io,
110  Foam::zero
111 )
112 :
113  regIOobject(io)
114 {
115  readContents();
116 }
117 
118 
119 template<class T, class BaseType>
121 (
122  const IOobject& io,
123  const label len
124 )
125 :
126  regIOobject(io)
127 {
128  if (!readContents())
129  {
131  }
132 }
133 
134 
135 template<class T, class BaseType>
137 (
138  const IOobject& io,
139  const UList<T>& content
140 )
141 :
142  regIOobject(io)
143 {
144  if (!readContents())
145  {
147  }
148 }
149 
150 
151 template<class T, class BaseType>
153 (
154  const IOobject& io,
155  List<T>&& content
156 )
157 :
158  regIOobject(io)
159 {
160  List<T>::transfer(content);
161 
162  readContents();
163 }
164 
165 
166 // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
167 
168 template<class T, class BaseType>
170 (
171  IOstreamOption streamOpt,
172  const bool writeOnProc
173 ) const
174 {
175  if
176  (
177  streamOpt.format() == IOstreamOption::BINARY
178  && overflows()
179  )
180  {
181  streamOpt.format(IOstreamOption::ASCII);
182 
184  << "Overall number of elements of CompactIOList of size "
185  << this->size() << " overflows the representation of a label"
186  << nl << " Switching to ascii writing" << endl;
187  }
188 
189  if (streamOpt.format() == IOstreamOption::ASCII)
190  {
191  // Change type to be non-compact format type
192  const word oldTypeName(typeName);
193 
194  const_cast<word&>(typeName) = IOList<T>::typeName;
195 
196  bool good = regIOobject::writeObject(streamOpt, writeOnProc);
197 
198  // Change type back
199  const_cast<word&>(typeName) = oldTypeName;
200 
201  return good;
202  }
203 
204  return regIOobject::writeObject(streamOpt, writeOnProc);
205 }
206 
207 
208 template<class T, class BaseType>
210 {
211  return (os << *this).good();
212 }
213 
214 
215 // * * * * * * * * * * * * * * * Member Operators * * * * * * * * * * * * * //
216 
217 template<class T, class BaseType>
219 (
220  const CompactIOList<T, BaseType>& rhs
221 )
222 {
223  List<T>::operator=(rhs);
224 }
225 
226 
227 // * * * * * * * * * * * * * * * Friend Operators * * * * * * * * * * * * * //
228 
229 template<class T, class BaseType>
230 Foam::Istream& Foam::operator>>
231 (
232  Foam::Istream& is,
234 )
235 {
236  // Read compact
237  const labelList start(is);
238  const List<BaseType> elems(is);
239 
240  // Convert
241  L.setSize(start.size()-1);
242 
243  forAll(L, i)
244  {
245  T& subList = L[i];
246 
247  label index = start[i];
248  subList.setSize(start[i+1] - index);
249 
250  forAll(subList, j)
251  {
252  subList[j] = elems[index++];
253  }
254  }
255 
256  return is;
257 }
258 
259 
260 template<class T, class BaseType>
261 Foam::Ostream& Foam::operator<<
262 (
263  Foam::Ostream& os,
265 )
266 {
267  // Keep ASCII writing same
268  if (os.format() == IOstreamOption::ASCII)
269  {
270  os << static_cast<const List<T>&>(L);
271  }
272  else
273  {
274  // Convert to compact format
275  labelList start(L.size()+1);
276 
277  start[0] = 0;
278  for (label i = 1; i < start.size(); i++)
279  {
280  const label prev = start[i-1];
281  start[i] = prev+L[i-1].size();
282 
283  if (start[i] < prev)
284  {
286  << "Overall number of elements " << start[i]
287  << " of CompactIOList of size "
288  << L.size() << " overflows the representation of a label"
289  << endl << "Please recompile with a larger representation"
290  << " for label" << exit(FatalIOError);
291  }
292  }
293 
294  List<BaseType> elems(start[start.size()-1]);
295 
296  label elemI = 0;
297  forAll(L, i)
298  {
299  const T& subList = L[i];
300 
301  forAll(subList, j)
302  {
303  elems[elemI++] = subList[j];
304  }
305  }
306  os << start << elems;
307  }
308 
309  return os;
310 }
311 
312 
313 // ************************************************************************* //
errorManipArg< error, int > exit(error &err, const int errNo=1)
Definition: errorManip.H:125
patchWriters resize(patchIds.size())
const vector L(dict.get< vector >("L"))
CompactIOList(const CompactIOList &)=default
Default copy construct.
A 1D array of objects of type <T>, where the size of the vector is known and used for subscript bound...
Definition: BitOps.H:56
An Istream is an abstract base class for all input systems (streams, files, token lists etc)...
Definition: Istream.H:57
constexpr char nl
The newline &#39;\n&#39; character (0x0a)
Definition: Ostream.H:50
Ostream & endl(Ostream &os)
Add newline and flush stream.
Definition: Ostream.H:531
A simple container for options an IOstream can normally have.
#define forAll(list, i)
Loop across all elements in list.
Definition: stdFoam.H:421
word name(const expressions::valueTypeCode typeCode)
A word representation of a valueTypeCode. Empty for expressions::valueTypeCode::INVALID.
Definition: exprTraits.C:127
An Ostream is an abstract base class for all output systems (streams, files, token lists...
Definition: Ostream.H:56
virtual bool writeObject(IOstreamOption streamOpt, const bool writeOnProc) const
Write using stream options. Checks for overflow in binary.
OBJstream os(runTime.globalPath()/outputName)
A List of objects of type <T> with automated input and output using a compact storage. Behaves like IOList except when binary output in case it writes a CompactListList.
Definition: CompactIOList.H:49
const volScalarField & T
#define WarningInFunction
Report a warning using Foam::Warning.
#define FatalIOErrorInFunction(ios)
Report an error message using Foam::FatalIOError.
Definition: error.H:627
regIOobject is an abstract class derived from IOobject to handle automatic object registration with t...
Definition: regIOobject.H:66
A class representing the concept of 0 (zero) that can be used to avoid manipulating objects known to ...
Definition: zero.H:57
List< label > labelList
A List of labels.
Definition: List.H:62
IOobject io("surfaceFilmProperties", mesh.time().constant(), mesh, IOobject::READ_IF_PRESENT, IOobject::NO_WRITE, IOobject::NO_REGISTER)
virtual bool writeData(Ostream &) const
Pure virtual writeData function.
Defines the attributes of an object for which implicit objectRegistry management is supported...
Definition: IOobject.H:172
streamFormat format() const noexcept
Get the current stream format.
IOerror FatalIOError
Error stream (stdout output on all processes), with additional &#39;FOAM FATAL IO ERROR&#39; header text and ...