ListHashTableIO.C
Go to the documentation of this file.
1 /*---------------------------------------------------------------------------*\
2  ========= |
3  \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
4  \\ / O peration | Website: https://openfoam.org
5  \\ / A nd | Copyright (C) 2011-2019 OpenFOAM Foundation
6  \\/ M anipulation |
7 -------------------------------------------------------------------------------
8 License
9  This file is part of OpenFOAM.
10 
11  OpenFOAM is free software: you can redistribute it and/or modify it
12  under the terms of the GNU General Public License as published by
13  the Free Software Foundation, either version 3 of the License, or
14  (at your option) any later version.
15 
16  OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
17  ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
18  FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
19  for more details.
20 
21  You should have received a copy of the GNU General Public License
22  along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
23 
24 \*---------------------------------------------------------------------------*/
25 
26 #include "ListHashTable.H"
27 #include "Istream.H"
28 #include "Ostream.H"
29 
30 // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
31 
32 template<class T, class Key, class Hash>
34 (
35  Istream& is,
36  const label size
37 )
38 :
40  keys_(ListHashTableCore::canonicalSize(size)),
41  objects_(ListHashTableCore::canonicalSize(size)),
42  nElmts_(0),
43  endIter_(*this, keys_.size(), 0),
44  endConstIter_(*this, keys_.size(), 0)
45 {
46  if (size < 1)
47  {
49  << "Illegal size " << size << " for ListHashTable."
50  << " Minimum size is 1" << abort(FatalError);
51  }
52 
53  operator>>(is, *this);
54 }
55 
56 
57 // * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * * //
58 
59 template<class T, class Key, class Hash>
62 {
63  label used = 0;
64  label maxChain = 0;
65  unsigned avgChain = 0;
66 
67  // Find first non-empty entry
68  forAll(keys_, hashIdx)
69  {
70  const label count = keys_[hashIdx].size();
71  if (count)
72  {
73  ++used;
74  avgChain += count;
75 
76  if (maxChain < count)
77  {
78  maxChain = count;
79  }
80  }
81  }
82 
83  os << "ListHashTable<T,Key,Hash>"
84  << " elements:" << size() << " slots:" << used << "/" << keys_.size()
85  << " chaining(avg/max):" << (used ? float(avgChain/used) : 0)
86  << "/" << maxChain << endl;
87 
88  return os;
89 }
90 
91 
92 // * * * * * * * * * * * * * * * IOstream Operators * * * * * * * * * * * * //
93 
94 template<class T, class Key, class Hash>
96 {
97  is.fatalCheck("operator>>(Istream&, ListHashTable<T, Key, Hash>&)");
98 
99  // Anull list
100  L.clear();
101 
102  is.fatalCheck("operator>>(Istream&, ListHashTable<T, Key, Hash>&)");
103 
104  token firstToken(is);
105 
106  is.fatalCheck
107  (
108  "operator>>(Istream&, ListHashTable<T, Key, Hash>&) : "
109  "reading first token"
110  );
111 
112  if (firstToken.isLabel())
113  {
114  label s = firstToken.labelToken();
115 
116  // Read beginning of contents
117  char delimiter = is.readBeginList("ListHashTable<T, Key, Hash>");
118 
119  if (s)
120  {
121  if (2*s > L.keys_.size())
122  {
123  L.resize(2*s);
124  }
125 
126  if (delimiter == token::BEGIN_LIST)
127  {
128  for (label i=0; i<s; i++)
129  {
130  Key key;
131  is >> key;
132  L.insert(key, pTraits<T>(is));
133 
134  is.fatalCheck
135  (
136  "operator>>(Istream&, ListHashTable<T, Key, Hash>&)"
137  " : reading entry"
138  );
139  }
140  }
141  else
142  {
144  (
145  is
146  ) << "incorrect first token, '(', found " << firstToken.info()
147  << exit(FatalIOError);
148  }
149  }
150 
151  // Read end of contents
152  is.readEndList("ListHashTable");
153  }
154  else if (firstToken.isPunctuation())
155  {
156  if (firstToken.pToken() != token::BEGIN_LIST)
157  {
159  (
160  is
161  ) << "incorrect first token, '(', found " << firstToken.info()
162  << exit(FatalIOError);
163  }
164 
165  token lastToken(is);
166  while
167  (
168  !(
169  lastToken.isPunctuation()
170  && lastToken.pToken() == token::END_LIST
171  )
172  )
173  {
174  is.putBack(lastToken);
175 
176  Key key;
177  is >> key;
178 
179  T element;
180  is >> element;
181 
182  L.insert(key, element);
183 
184  is.fatalCheck
185  (
186  "operator>>(Istream&, ListHashTable<T, Key, Hash>&) : "
187  "reading entry"
188  );
189 
190  is >> lastToken;
191  }
192  }
193  else
194  {
196  (
197  is
198  ) << "incorrect first token, expected <int> or '(', found "
199  << firstToken.info()
200  << exit(FatalIOError);
201  }
202 
203  is.fatalCheck("operator>>(Istream&, ListHashTable<T, Key, Hash>&)");
204 
205  return is;
206 }
207 
208 
209 template<class T, class Key, class Hash>
210 Foam::Ostream& Foam::operator<<
211 (
212  Ostream& os,
213  const ListHashTable<T, Key, Hash>& L)
214 {
215  // Write size and start delimiter
216  os << nl << L.size() << nl << token::BEGIN_LIST << nl;
217 
218  // Write contents
219  for
220  (
222  iter != L.end();
223  ++iter
224  )
225  {
226  os << iter.key() << token::SPACE << iter() << nl;
227  }
228 
229  // Write end delimiter
230  os << token::END_LIST;
231 
232  // Check state of IOstream
233  os.check("Ostream& operator<<(Ostream&, const ListHashTable&)");
234 
235  return os;
236 }
237 
238 
239 // ************************************************************************* //
#define forAll(list, i)
Loop across all elements in list.
Definition: UList.H:434
void fatalCheck(const char *operation) const
Check IOstream status for given operation.
Definition: IOstream.C:105
An Istream is an abstract base class for all input systems (streams, files, token lists etc)....
Definition: Istream.H:60
char readEndList(const char *funcName)
Definition: Istream.C:148
char readBeginList(const char *funcName)
Definition: Istream.C:127
void putBack(const token &)
Put back token.
Definition: Istream.C:30
STL conforming hash table using contiguous lists rather than linked lists.
bool insert(const Key &key, const T &newElmt)
Insert a new hashed entry.
friend Istream & operator>>(Istream &, ListHashTable< T, Key, Hash > &)
Ostream & printInfo(Ostream &) const
Print information.
label size() const
Return number of elements in table.
const iterator & end()
Iterator set to beyond the end of the ListHashTable.
Iterator< const T &, const ListHashTable< T, Key, Hash > & > const_iterator
ListHashTable(const label size=128)
Construct given initial table size.
Definition: ListHashTable.C:62
iterator begin()
Iterator set to the beginning of the ListHashTable.
void clear()
Clear all entries from table.
void resize(const label newSize)
Resize the hash table for efficiency.
An Ostream is an abstract base class for all output systems (streams, files, token lists,...
Definition: Ostream.H:57
A token holds items read from Istream.
Definition: token.H:73
@ BEGIN_LIST
Definition: token.H:106
@ END_LIST
Definition: token.H:107
#define FatalIOErrorInFunction(ios)
Report an error message using Foam::FatalIOError.
Definition: error.H:318
#define FatalErrorInFunction
Report an error message using Foam::FatalError.
Definition: error.H:306
gmvFile<< "tracers "<< particles.size()<< nl;forAllConstIter(Cloud< passiveParticle >, particles, iter){ gmvFile<< iter().position().x()<< " ";}gmvFile<< nl;forAllConstIter(Cloud< passiveParticle >, particles, iter){ gmvFile<< iter().position().y()<< " ";}gmvFile<< nl;forAllConstIter(Cloud< passiveParticle >, particles, iter){ gmvFile<< iter().position().z()<< " ";}gmvFile<< nl;forAll(lagrangianScalarNames, i){ word name=lagrangianScalarNames[i];IOField< scalar > s(IOobject(name, runTime.name(), cloud::prefix, mesh, IOobject::MUST_READ, IOobject::NO_WRITE))
errorManipArg< error, int > exit(error &err, const int errNo=1)
Definition: errorManip.H:124
intWM_LABEL_SIZE_t label
A label is an int32_t or int64_t as specified by the pre-processor macro WM_LABEL_SIZE.
Definition: label.H:59
Ostream & endl(Ostream &os)
Add newline and flush stream.
Definition: Ostream.H:251
errorManip< error > abort(error &err)
Definition: errorManip.H:131
Istream & operator>>(Istream &, directionInfo &)
IOerror FatalIOError
error FatalError
label count(const ListType &l, typename ListType::const_reference x)
Count the number of occurrences of a value in a list.
static const char nl
Definition: Ostream.H:260
void T(FieldField< Field, Type > &f1, const FieldField< Field, Type > &f2)
Template-invariant bits for ListHashTable.
Definition: ListHashTable.H:77