dictionary.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-2021 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 "dictionary.H"
27 #include "primitiveEntry.H"
28 #include "dictionaryEntry.H"
29 #include "regExp.H"
30 #include "OSHA1stream.H"
31 #include "DynamicList.H"
32 #include "inputSyntaxEntry.H"
33 #include "fileOperation.H"
34 #include "stringOps.H"
35 
36 /* * * * * * * * * * * * * * * Static Member Data * * * * * * * * * * * * * */
37 
38 namespace Foam
39 {
40  defineTypeNameAndDebug(dictionary, 0);
41 }
42 
44 
46 (
47  Foam::debug::infoSwitch("writeOptionalEntries", 0)
48 );
49 
50 
51 // * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
52 
53 const Foam::entry* Foam::dictionary::lookupDotScopedSubEntryPtr
54 (
55  const word& keyword,
56  bool recursive,
57  bool patternMatch
58 ) const
59 {
60  string::size_type dotPos = keyword.find('.');
61 
62  if (dotPos == string::npos)
63  {
64  // Non-scoped lookup
65  return lookupEntryPtr(keyword, recursive, patternMatch);
66  }
67  else
68  {
69  if (dotPos == 0)
70  {
71  // Starting with a '.'. Go up for every 2nd '.' found
72 
73  const dictionary* dictPtr = this;
74 
75  string::size_type begVar = dotPos + 1;
76  string::const_iterator iter = keyword.begin() + begVar;
77  string::size_type endVar = begVar;
78  while (iter != keyword.end() && *iter == '.')
79  {
80  ++iter;
81  ++endVar;
82 
83  // Go to parent
84  if (&dictPtr->parent_ == &dictionary::null)
85  {
87  << "No parent of current dictionary"
88  << " when searching for "
89  << keyword.substr(begVar, keyword.size() - begVar)
90  << exit(FatalIOError);
91  }
92  dictPtr = &dictPtr->parent_;
93  }
94 
95  return dictPtr->lookupScopedSubEntryPtr
96  (
97  keyword.substr(endVar),
98  false,
99  patternMatch
100  );
101  }
102  else
103  {
104  // Extract the first word
105  word firstWord = keyword.substr(0, dotPos);
106 
107  const entry* entPtr = lookupDotScopedSubEntryPtr
108  (
109  firstWord,
110  false, // recursive
111  patternMatch
112  );
113 
114  if (!entPtr)
115  {
116  // Fall back to finding key with '.' so e.g. if keyword is
117  // a.b.c.d it would try
118  // a.b, a.b.c, a.b.c.d
119 
120  string::size_type nextDotPos = keyword.find
121  (
122  '.',
123  dotPos + 1
124  );
125 
126  while (true)
127  {
128  const entry* subEntPtr = lookupEntryPtr
129  (
130  keyword.substr(0, nextDotPos),
131  false, // recursive,
132  patternMatch
133  );
134  if (nextDotPos == string::npos)
135  {
136  // Parsed the whole word. Return entry or null.
137  return subEntPtr;
138  }
139 
140  if (subEntPtr && subEntPtr->isDict())
141  {
142  return subEntPtr->dict().lookupDotScopedSubEntryPtr
143  (
144  keyword.substr
145  (
146  nextDotPos,
147  keyword.size() - nextDotPos
148  ),
149  false,
150  patternMatch
151  );
152  }
153 
154  nextDotPos = keyword.find('.', nextDotPos + 1);
155  }
156  }
157 
158  if (entPtr->isDict())
159  {
160  return entPtr->dict().lookupDotScopedSubEntryPtr
161  (
162  keyword.substr(dotPos, keyword.size() - dotPos),
163  false,
164  patternMatch
165  );
166  }
167  else
168  {
169  return nullptr;
170  }
171  }
172  }
173 }
174 
175 
176 const Foam::entry* Foam::dictionary::lookupSlashScopedSubEntryPtr
177 (
178  const word& keyword,
179  bool recursive,
180  bool patternMatch
181 ) const
182 {
183  string::size_type slashPos = keyword.find('/');
184 
185  if (slashPos == string::npos)
186  {
187  // Non-scoped lookup
188  return lookupEntryPtr(keyword, recursive, patternMatch);
189  }
190  else
191  {
192  // Extract the first word
193  word firstWord = keyword.substr(0, slashPos);
194  slashPos++;
195 
196  if (firstWord == ".")
197  {
198  return lookupScopedSubEntryPtr
199  (
200  keyword.substr(slashPos),
201  false,
202  patternMatch
203  );
204  }
205  else if (firstWord == "..")
206  {
207  // Go to parent
208  if (&parent_ == &dictionary::null)
209  {
211  << "No parent of current dictionary"
212  << " when searching for "
213  << keyword.substr(slashPos, keyword.size() - slashPos)
214  << exit(FatalIOError);
215  }
216 
217  return parent_.lookupScopedSubEntryPtr
218  (
219  keyword.substr(slashPos),
220  false,
221  patternMatch
222  );
223  }
224  else
225  {
226  const entry* entPtr = lookupScopedSubEntryPtr
227  (
228  firstWord,
229  false, // recursive
230  patternMatch
231  );
232 
233  if (!entPtr)
234  {
235  // Fall back to finding key with '/' so e.g. if keyword is
236  // a/b/c/d it would try
237  // a/b, a/b/c, a/b/c/d
238 
239  string::size_type nextSlashPos = keyword.find
240  (
241  '/',
242  slashPos
243  );
244 
245  while (true)
246  {
247  const entry* subEntPtr = lookupEntryPtr
248  (
249  keyword.substr(0, nextSlashPos),
250  false, // recursive,
251  patternMatch
252  );
253 
254  if (nextSlashPos == string::npos)
255  {
256  // Parsed the whole word. Return entry or null.
257  return subEntPtr;
258  }
259 
260  nextSlashPos++;
261 
262  if (subEntPtr && subEntPtr->isDict())
263  {
264  return subEntPtr->dict().lookupScopedSubEntryPtr
265  (
266  keyword.substr
267  (
268  nextSlashPos,
269  keyword.size() - nextSlashPos
270  ),
271  false,
272  patternMatch
273  );
274  }
275 
276  nextSlashPos = keyword.find('/', nextSlashPos);
277  }
278  }
279 
280  if (entPtr->isDict())
281  {
282  return entPtr->dict().lookupScopedSubEntryPtr
283  (
284  keyword.substr(slashPos, keyword.size() - slashPos),
285  false,
286  patternMatch
287  );
288  }
289  else
290  {
291  return nullptr;
292  }
293  }
294  }
295 }
296 
297 
298 const Foam::entry* Foam::dictionary::lookupScopedSubEntryPtr
299 (
300  const word& keyword,
301  bool recursive,
302  bool patternMatch
303 ) const
304 {
306  {
307  return lookupDotScopedSubEntryPtr(keyword, recursive, patternMatch);
308  }
309  else
310  {
311  // Check for the dictionary boundary marker
312  const string::size_type emarkPos = keyword.find('!');
313 
314  if (emarkPos == string::npos || emarkPos == 0)
315  {
316  // Lookup in this dictionary
317 
318  return lookupSlashScopedSubEntryPtr
319  (
320  keyword,
321  recursive,
322  patternMatch
323  );
324  }
325  else
326  {
327  // Lookup in the dictionary specified by file name
328  // created from the part of the keyword before the '!'
329 
330  fileName fName = keyword.substr(0, emarkPos);
331 
332  if (!fName.isAbsolute())
333  {
334  fName = topDict().name().path()/fName;
335  }
336 
337  if (fName == topDict().name())
338  {
340  << "Attempt to re-read current dictionary " << fName
341  << " for keyword "
342  << keyword
343  << exit(FatalIOError);
344  }
345 
346  const word localKeyword = keyword.substr
347  (
348  emarkPos + 1,
349  keyword.size() - emarkPos - 1
350  );
351 
352  includedDictionary dict(fName, *this);
353 
354  const Foam::entry* entryPtr = dict.lookupScopedEntryPtr
355  (
356  localKeyword,
357  recursive,
358  patternMatch
359  );
360 
361  if (!entryPtr)
362  {
364  << "keyword " << localKeyword
365  << " is undefined in dictionary "
366  << dict.name()
367  << exit(FatalIOError);
368  }
369 
370  return entryPtr->clone(*this).ptr();
371  }
372  }
373 }
374 
375 
376 bool Foam::dictionary::findInPatterns
377 (
378  const bool patternMatch,
379  const word& Keyword,
381  DLList<autoPtr<regExp>>::const_iterator& reLink
382 ) const
383 {
384  if (patternEntries_.size())
385  {
386  while (wcLink != patternEntries_.end())
387  {
388  if
389  (
390  patternMatch
391  ? reLink()->match(Keyword)
392  : wcLink()->keyword() == Keyword
393  )
394  {
395  return true;
396  }
397 
398  ++reLink;
399  ++wcLink;
400  }
401  }
402 
403  return false;
404 }
405 
406 
407 bool Foam::dictionary::findInPatterns
408 (
409  const bool patternMatch,
410  const word& Keyword,
411  DLList<entry*>::iterator& wcLink,
412  DLList<autoPtr<regExp>>::iterator& reLink
413 )
414 {
415  if (patternEntries_.size())
416  {
417  while (wcLink != patternEntries_.end())
418  {
419  if
420  (
421  patternMatch
422  ? reLink()->match(Keyword)
423  : wcLink()->keyword() == Keyword
424  )
425  {
426  return true;
427  }
428 
429  ++reLink;
430  ++wcLink;
431  }
432  }
433 
434  return false;
435 }
436 
437 
438 // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
439 
441 :
442  parent_(dictionary::null)
443 {}
444 
445 
447 :
448  dictionaryName(name),
449  parent_(dictionary::null)
450 {}
451 
452 
454 (
455  const dictionary& parentDict,
456  const dictionary& dict
457 )
458 :
459  dictionaryName(dict.name()),
460  IDLList<entry>(dict, *this),
461  parent_(parentDict)
462 {
463  forAllIter(IDLList<entry>, *this, iter)
464  {
465  hashedEntries_.insert(iter().keyword(), &iter());
466 
467  if (iter().keyword().isPattern())
468  {
469  patternEntries_.insert(&iter());
470  patternRegexps_.insert
471  (
472  autoPtr<regExp>(new regExp(iter().keyword()))
473  );
474  }
475  }
476 }
477 
478 
480 (
481  const dictionary& dict
482 )
483 :
484  dictionaryName(dict.name()),
485  IDLList<entry>(dict, *this),
486  parent_(dictionary::null)
487 {
488  forAllIter(IDLList<entry>, *this, iter)
489  {
490  hashedEntries_.insert(iter().keyword(), &iter());
491 
492  if (iter().keyword().isPattern())
493  {
494  patternEntries_.insert(&iter());
495  patternRegexps_.insert
496  (
497  autoPtr<regExp>(new regExp(iter().keyword()))
498  );
499  }
500  }
501 }
502 
503 
505 (
506  dictionary&& dict
507 )
508 :
509  dictionaryName(move(dict.name())),
510  IDLList<entry>(move(dict)),
511  hashedEntries_(move(dict.hashedEntries_)),
512  parent_(dict.parent_),
513  patternEntries_(move(dict.patternEntries_)),
514  patternRegexps_(move(dict.patternRegexps_))
515 {}
516 
517 
519 (
520  const dictionary* dictPtr
521 )
522 :
523  parent_(dictionary::null)
524 {
525  if (dictPtr)
526  {
527  operator=(*dictPtr);
528  }
529 }
530 
531 
533 (
534  const dictionary& parentDict,
535  dictionary&& dict
536 )
537 :
538  dictionaryName(move(dict.name())),
539  IDLList<entry>(move(dict)),
540  hashedEntries_(move(dict.hashedEntries_)),
541  parent_(parentDict),
542  patternEntries_(move(dict.patternEntries_)),
543  patternRegexps_(move(dict.patternRegexps_))
544 {
545  if (parentDict.name() != fileName::null)
546  {
547  name() = parentDict.name()/name();
548  }
549 }
550 
551 
553 {
554  return autoPtr<dictionary>(new dictionary(*this));
555 }
556 
557 
558 // * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * //
559 
561 {
562  // cerr<< "~dictionary() " << name() << " " << long(this) << std::endl;
563 }
564 
565 
566 // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
567 
569 {
570  const dictionary& p = parent();
571 
572  if (&p != this && !p.name().empty())
573  {
574  return p.topDict();
575  }
576  else
577  {
578  return *this;
579  }
580 }
581 
582 
584 {
585  if (size())
586  {
587  return first()->startLineNumber();
588  }
589  else
590  {
591  return -1;
592  }
593 }
594 
595 
597 {
598  if (size())
599  {
600  return last()->endLineNumber();
601  }
602  else
603  {
604  return -1;
605  }
606 }
607 
608 
610 {
611  OSHA1stream os;
612 
613  // Process entries
614  forAllConstIter(IDLList<entry>, *this, iter)
615  {
616  os << *iter;
617  }
618 
619  return os.digest();
620 }
621 
622 
624 {
625  // Serialise dictionary into a string
626  OStringStream os;
627  write(os, false);
628  IStringStream is(os.str());
629 
630  // Parse string as tokens
632  token t;
633  while (is.read(t))
634  {
635  tokens.append(t);
636  }
637 
638  return tokenList(move(tokens));
639 }
640 
641 
643 (
644  const word& keyword,
645  bool recursive,
646  bool patternMatch
647 ) const
648 {
649  if (hashedEntries_.found(keyword))
650  {
651  return true;
652  }
653  else
654  {
655  if (patternMatch && patternEntries_.size())
656  {
658  patternEntries_.begin();
660  patternRegexps_.begin();
661 
662  // Find in patterns using regular expressions only
663  if (findInPatterns(patternMatch, keyword, wcLink, reLink))
664  {
665  return true;
666  }
667  }
668 
669  if (recursive && &parent_ != &dictionary::null)
670  {
671  return parent_.found(keyword, recursive, patternMatch);
672  }
673  else
674  {
675  return false;
676  }
677  }
678 }
679 
680 
682 (
683  const word& keyword,
684  bool recursive,
685  bool patternMatch
686 ) const
687 {
688  HashTable<entry*>::const_iterator iter = hashedEntries_.find(keyword);
689 
690  if (iter == hashedEntries_.end())
691  {
692  if (patternMatch && patternEntries_.size())
693  {
695  patternEntries_.begin();
697  patternRegexps_.begin();
698 
699  // Find in patterns using regular expressions only
700  if (findInPatterns(patternMatch, keyword, wcLink, reLink))
701  {
702  return wcLink();
703  }
704  }
705 
706  if (recursive && &parent_ != &dictionary::null)
707  {
708  return parent_.lookupEntryPtr(keyword, recursive, patternMatch);
709  }
710  else
711  {
712  return nullptr;
713  }
714  }
715 
716  return iter();
717 }
718 
719 
721 (
722  const word& keyword,
723  bool recursive,
724  bool patternMatch
725 )
726 {
727  HashTable<entry*>::iterator iter = hashedEntries_.find(keyword);
728 
729  if (iter == hashedEntries_.end())
730  {
731  if (patternMatch && patternEntries_.size())
732  {
733  DLList<entry*>::iterator wcLink =
734  patternEntries_.begin();
736  patternRegexps_.begin();
737 
738  // Find in patterns using regular expressions only
739  if (findInPatterns(patternMatch, keyword, wcLink, reLink))
740  {
741  return wcLink();
742  }
743  }
744 
745  if (recursive && &parent_ != &dictionary::null)
746  {
747  return const_cast<dictionary&>(parent_).lookupEntryPtr
748  (
749  keyword,
750  recursive,
751  patternMatch
752  );
753  }
754  else
755  {
756  return nullptr;
757  }
758  }
759 
760  return iter();
761 }
762 
763 
765 (
766  const wordList& keywords,
767  bool recursive,
768  bool patternMatch
769 ) const
770 {
771  const entry* result = nullptr;
772 
773  forAll(keywords, keywordi)
774  {
775  const entry* entryPtr =
776  lookupEntryPtr(keywords[keywordi], recursive, patternMatch);
777 
778  if (entryPtr)
779  {
780  if (result)
781  {
782  IOWarningInFunction((*this))
783  << "Duplicate backwards compatible keywords \""
784  << result->keyword() << "\" and \"" << entryPtr->keyword()
785  << "\" are defined in dictionary " << name() << endl
786  << "The preferred keyword for this entry is \""
787  << keywords[0] << "\"" << endl;
788  }
789  else
790  {
791  result = entryPtr;
792  }
793  }
794  }
795 
796  return result;
797 }
798 
799 
801 (
802  const word& keyword,
803  bool recursive,
804  bool patternMatch
805 ) const
806 {
807  const entry* entryPtr = lookupEntryPtr(keyword, recursive, patternMatch);
808 
809  if (entryPtr == nullptr)
810  {
812  << "keyword " << keyword << " is undefined in dictionary "
813  << name()
814  << exit(FatalIOError);
815  }
816 
817  return *entryPtr;
818 }
819 
820 
822 (
823  const wordList& keywords,
824  bool recursive,
825  bool patternMatch
826 ) const
827 {
828  const entry* entryPtr =
829  lookupEntryPtrBackwardsCompatible(keywords, recursive, patternMatch);
830 
831  if (entryPtr == nullptr)
832  {
833  // Generate error message using the first keyword
834  return lookupEntry(keywords[0], recursive, patternMatch);
835  }
836  else
837  {
838  return *entryPtr;
839  }
840 }
841 
842 
844 (
845  const word& keyword,
846  bool recursive,
847  bool patternMatch
848 ) const
849 {
850  return lookupEntry(keyword, recursive, patternMatch).stream();
851 }
852 
853 
855 (
856  const wordList& keywords,
857  bool recursive,
858  bool patternMatch
859 ) const
860 {
862  (
863  keywords,
864  recursive,
865  patternMatch
866  ).stream();
867 }
868 
869 
871 (
872  const word& keyword,
873  bool recursive,
874  bool patternMatch
875 ) const
876 {
877  // '!' indicates the top-level directory in the "slash" syntax
878  // ':' indicates the top-level directory in the "dot" syntax
879  if
880  (
881  (functionEntries::inputSyntaxEntry::slash() && keyword[0] == '!')
882  || (functionEntries::inputSyntaxEntry::dot() && keyword[0] == ':')
883  )
884  {
885  // Go up to top level
886  const dictionary* dictPtr = this;
887  while (&dictPtr->parent_ != &dictionary::null)
888  {
889  dictPtr = &dictPtr->parent_;
890  }
891 
892  // At top. Recurse to find entries
893  return dictPtr->lookupScopedSubEntryPtr
894  (
895  keyword.substr(1, keyword.size() - 1),
896  false,
897  patternMatch
898  );
899  }
900  else
901  {
902  return lookupScopedSubEntryPtr
903  (
904  keyword,
905  recursive,
906  patternMatch
907  );
908  }
909 }
910 
911 
913 {
914  word varName = keyword(1, keyword.size() - 1);
915 
916  // Lookup the variable name in the given dictionary
917  const entry* ePtr = lookupScopedEntryPtr(varName, true, true);
918 
919  // If defined insert its entries into this dictionary
920  if (ePtr != nullptr)
921  {
922  const dictionary& addDict = ePtr->dict();
923 
924  forAllConstIter(IDLList<entry>, addDict, iter)
925  {
926  add(iter());
927  }
928 
929  return true;
930  }
931 
932  return false;
933 }
934 
935 
936 bool Foam::dictionary::isDict(const word& keyword) const
937 {
938  // Find non-recursive with patterns
939  const entry* entryPtr = lookupEntryPtr(keyword, false, true);
940 
941  if (entryPtr)
942  {
943  return entryPtr->isDict();
944  }
945  else
946  {
947  return false;
948  }
949 }
950 
951 
953 {
954  const entry* entryPtr = lookupEntryPtr(keyword, false, true);
955 
956  if (entryPtr)
957  {
958  return &entryPtr->dict();
959  }
960  else
961  {
962  return nullptr;
963  }
964 }
965 
966 
968 {
969  entry* entryPtr = lookupEntryPtr(keyword, false, true);
970 
971  if (entryPtr)
972  {
973  return &entryPtr->dict();
974  }
975  else
976  {
977  return nullptr;
978  }
979 }
980 
981 
982 const Foam::dictionary& Foam::dictionary::subDict(const word& keyword) const
983 {
984  const entry* entryPtr = lookupEntryPtr(keyword, false, true);
985 
986  if (entryPtr == nullptr)
987  {
989  << "keyword " << keyword << " is undefined in dictionary "
990  << name()
991  << exit(FatalIOError);
992  }
993  return entryPtr->dict();
994 }
995 
996 
998 {
999  entry* entryPtr = lookupEntryPtr(keyword, false, true);
1000 
1001  if (entryPtr == nullptr)
1002  {
1003  FatalIOErrorInFunction(*this)
1004  << "keyword " << keyword << " is undefined in dictionary "
1005  << name()
1006  << exit(FatalIOError);
1007  }
1008  return entryPtr->dict();
1009 }
1010 
1011 
1014  const word& keyword,
1015  const bool mustRead
1016 ) const
1017 {
1018  const entry* entryPtr = lookupEntryPtr(keyword, false, true);
1019 
1020  if (entryPtr == nullptr)
1021  {
1022  if (mustRead)
1023  {
1024  FatalIOErrorInFunction(*this)
1025  << "keyword " << keyword << " is undefined in dictionary "
1026  << name()
1027  << exit(FatalIOError);
1028  }
1029 
1030  return dictionary(*this, dictionary(name() + '/' + keyword));
1031  }
1032  else
1033  {
1034  return entryPtr->dict();
1035  }
1036 }
1037 
1038 
1041  const word& keyword
1042 ) const
1043 {
1044  const entry* entryPtr = lookupEntryPtr(keyword, false, true);
1045 
1046  if (entryPtr)
1047  {
1048  return entryPtr->dict();
1049  }
1050  else
1051  {
1052  return *this;
1053  }
1054 }
1055 
1056 
1058 {
1059  if (keyword == "")
1060  {
1061  return *this;
1062  }
1063  else
1064  {
1065  const entry* entPtr = lookupScopedEntryPtr
1066  (
1067  keyword,
1068  false,
1069  false
1070  );
1071  if (!entPtr || !entPtr->isDict())
1072  {
1073  FatalIOErrorInFunction(*this)
1074  << "keyword " << keyword
1075  << " is undefined in dictionary "
1076  << name() << " or is not a dictionary"
1077  << endl
1078  << "Valid keywords are " << keys()
1079  << exit(FatalIOError);
1080  }
1081  return entPtr->dict();
1082  }
1083 }
1084 
1085 
1087 {
1088  return const_cast<dictionary&>
1089  (
1090  const_cast<const dictionary*>(this)->scopedDict(keyword)
1091  );
1092 }
1093 
1094 
1096 {
1097  wordList keys(size());
1098 
1099  label nKeys = 0;
1100  forAllConstIter(IDLList<entry>, *this, iter)
1101  {
1102  keys[nKeys++] = iter().keyword();
1103  }
1104 
1105  return keys;
1106 }
1107 
1108 
1110 {
1111  return hashedEntries_.sortedToc();
1112 }
1113 
1114 
1116 {
1117  List<keyType> keys(size());
1118 
1119  label nKeys = 0;
1120  forAllConstIter(IDLList<entry>, *this, iter)
1121  {
1122  if (iter().keyword().isPattern() ? patterns : !patterns)
1123  {
1124  keys[nKeys++] = iter().keyword();
1125  }
1126  }
1127  keys.setSize(nKeys);
1128 
1129  return keys;
1130 }
1131 
1132 
1133 bool Foam::dictionary::add(entry* entryPtr, bool mergeEntry)
1134 {
1135  HashTable<entry*>::iterator iter = hashedEntries_.find
1136  (
1137  entryPtr->keyword()
1138  );
1139 
1140  if (mergeEntry && iter != hashedEntries_.end())
1141  {
1142  // Merge dictionary with dictionary
1143  if (iter()->isDict() && entryPtr->isDict())
1144  {
1145  iter()->dict().merge(entryPtr->dict());
1146  delete entryPtr;
1147 
1148  return true;
1149  }
1150  else
1151  {
1152  // Replace existing dictionary with entry or vice versa
1153  IDLList<entry>::replace(iter(), entryPtr);
1154  delete iter();
1155  hashedEntries_.erase(iter);
1156 
1157  if (hashedEntries_.insert(entryPtr->keyword(), entryPtr))
1158  {
1159  entryPtr->name() = name() + '/' + entryPtr->keyword();
1160 
1161  if (entryPtr->keyword().isPattern())
1162  {
1163  patternEntries_.insert(entryPtr);
1164  patternRegexps_.insert
1165  (
1166  autoPtr<regExp>(new regExp(entryPtr->keyword()))
1167  );
1168  }
1169 
1170  return true;
1171  }
1172  else
1173  {
1174  IOWarningInFunction((*this))
1175  << "problem replacing entry "<< entryPtr->keyword()
1176  << " in dictionary " << name() << endl;
1177 
1178  IDLList<entry>::remove(entryPtr);
1179  delete entryPtr;
1180  return false;
1181  }
1182  }
1183  }
1184 
1185  if (hashedEntries_.insert(entryPtr->keyword(), entryPtr))
1186  {
1187  entryPtr->name() = name() + '/' + entryPtr->keyword();
1188  IDLList<entry>::append(entryPtr);
1189 
1190  if (entryPtr->keyword().isPattern())
1191  {
1192  patternEntries_.insert(entryPtr);
1193  patternRegexps_.insert
1194  (
1195  autoPtr<regExp>(new regExp(entryPtr->keyword()))
1196  );
1197  }
1198 
1199  return true;
1200  }
1201  else
1202  {
1203  // If function entries are disabled allow duplicate entries
1205  {
1206  entryPtr->name() = name() + '/' + entryPtr->keyword();
1207  IDLList<entry>::append(entryPtr);
1208 
1209  return true;
1210  }
1211  else
1212  {
1213  IOWarningInFunction((*this))
1214  << "attempt to add entry "<< entryPtr->keyword()
1215  << " which already exists in dictionary " << name()
1216  << endl;
1217 
1218  delete entryPtr;
1219  return false;
1220  }
1221  }
1222 }
1223 
1224 
1225 void Foam::dictionary::add(const entry& e, bool mergeEntry)
1226 {
1227  add(e.clone(*this).ptr(), mergeEntry);
1228 }
1229 
1230 
1231 void Foam::dictionary::add(const keyType& k, const word& w, bool overwrite)
1232 {
1233  add(new primitiveEntry(k, token(w)), overwrite);
1234 }
1235 
1236 
1239  const keyType& k,
1240  const Foam::string& s,
1241  bool overwrite
1242 )
1243 {
1244  add(new primitiveEntry(k, token(s)), overwrite);
1245 }
1246 
1247 
1248 void Foam::dictionary::add(const keyType& k, const label l, bool overwrite)
1249 {
1250  add(new primitiveEntry(k, token(l)), overwrite);
1251 }
1252 
1253 
1254 void Foam::dictionary::add(const keyType& k, const scalar s, bool overwrite)
1255 {
1256  add(new primitiveEntry(k, token(s)), overwrite);
1257 }
1258 
1259 
1262  const keyType& k,
1263  const dictionary& d,
1264  bool mergeEntry
1265 )
1266 {
1267  add(new dictionaryEntry(k, *this, d), mergeEntry);
1268 }
1269 
1270 
1272 {
1273  entry* existingPtr = lookupEntryPtr(entryPtr->keyword(), false, true);
1274 
1275  // Clear dictionary so merge acts like overwrite
1276  if (existingPtr && existingPtr->isDict())
1277  {
1278  existingPtr->dict().clear();
1279  }
1280  add(entryPtr, true);
1281 }
1282 
1283 
1285 {
1286  set(e.clone(*this).ptr());
1287 }
1288 
1289 
1290 void Foam::dictionary::set(const keyType& k, const dictionary& d)
1291 {
1292  set(new dictionaryEntry(k, *this, d));
1293 }
1294 
1295 
1296 bool Foam::dictionary::remove(const word& Keyword)
1297 {
1298  HashTable<entry*>::iterator iter = hashedEntries_.find(Keyword);
1299 
1300  if (iter != hashedEntries_.end())
1301  {
1302  // Delete from patterns first
1303  DLList<entry*>::iterator wcLink =
1304  patternEntries_.begin();
1306  patternRegexps_.begin();
1307 
1308  // Find in pattern using exact match only
1309  if (findInPatterns(false, Keyword, wcLink, reLink))
1310  {
1311  patternEntries_.remove(wcLink);
1312  patternRegexps_.remove(reLink);
1313  }
1314 
1315  IDLList<entry>::remove(iter());
1316  delete iter();
1317  hashedEntries_.erase(iter);
1318 
1319  return true;
1320  }
1321  else
1322  {
1323  return false;
1324  }
1325 }
1326 
1327 
1330  const keyType& oldKeyword,
1331  const keyType& newKeyword,
1332  bool forceOverwrite
1333 )
1334 {
1335  // No change
1336  if (oldKeyword == newKeyword)
1337  {
1338  return false;
1339  }
1340 
1341  HashTable<entry*>::iterator iter = hashedEntries_.find(oldKeyword);
1342 
1343  // oldKeyword not found - do nothing
1344  if (iter == hashedEntries_.end())
1345  {
1346  return false;
1347  }
1348 
1349  if (iter()->keyword().isPattern())
1350  {
1351  FatalIOErrorInFunction(*this)
1352  << "Old keyword "<< oldKeyword
1353  << " is a pattern."
1354  << "Pattern replacement not yet implemented."
1355  << exit(FatalIOError);
1356  }
1357 
1358 
1359  HashTable<entry*>::iterator iter2 = hashedEntries_.find(newKeyword);
1360 
1361  // newKeyword already exists
1362  if (iter2 != hashedEntries_.end())
1363  {
1364  if (forceOverwrite)
1365  {
1366  if (iter2()->keyword().isPattern())
1367  {
1368  // Delete from patterns first
1369  DLList<entry*>::iterator wcLink =
1370  patternEntries_.begin();
1372  patternRegexps_.begin();
1373 
1374  // Find in patterns using exact match only
1375  if (findInPatterns(false, iter2()->keyword(), wcLink, reLink))
1376  {
1377  patternEntries_.remove(wcLink);
1378  patternRegexps_.remove(reLink);
1379  }
1380  }
1381 
1382  IDLList<entry>::replace(iter2(), iter());
1383  delete iter2();
1384  hashedEntries_.erase(iter2);
1385 
1386  }
1387  else
1388  {
1390  (
1391  *this
1392  ) << "cannot rename keyword "<< oldKeyword
1393  << " to existing keyword " << newKeyword
1394  << " in dictionary " << name() << endl;
1395  return false;
1396  }
1397  }
1398 
1399  // Change name and HashTable, but leave DL-List untouched
1400  iter()->keyword() = newKeyword;
1401  iter()->name() = name() + '/' + newKeyword;
1402  hashedEntries_.erase(oldKeyword);
1403  hashedEntries_.insert(newKeyword, iter());
1404 
1405  if (newKeyword.isPattern())
1406  {
1407  patternEntries_.insert(iter());
1408  patternRegexps_.insert
1409  (
1410  autoPtr<regExp>(new regExp(newKeyword))
1411  );
1412  }
1413 
1414  return true;
1415 }
1416 
1417 
1419 {
1420  // Check for assignment to self
1421  if (this == &dict)
1422  {
1423  FatalIOErrorInFunction(*this)
1424  << "attempted merge to self for dictionary " << name()
1425  << abort(FatalIOError);
1426  }
1427 
1428  bool changed = false;
1429 
1430  forAllConstIter(IDLList<entry>, dict, iter)
1431  {
1432  HashTable<entry*>::iterator fnd = hashedEntries_.find(iter().keyword());
1433 
1434  if (fnd != hashedEntries_.end())
1435  {
1436  // Recursively merge sub-dictionaries
1437  // TODO: merge without copying
1438  if (fnd()->isDict() && iter().isDict())
1439  {
1440  if (fnd()->dict().merge(iter().dict()))
1441  {
1442  changed = true;
1443  }
1444  }
1445  else
1446  {
1447  add(iter().clone(*this).ptr(), true);
1448  changed = true;
1449  }
1450  }
1451  else
1452  {
1453  // Not found - just add
1454  add(iter().clone(*this).ptr());
1455  changed = true;
1456  }
1457  }
1458 
1459  return changed;
1460 }
1461 
1462 
1464 {
1466  hashedEntries_.clear();
1467  patternEntries_.clear();
1468  patternRegexps_.clear();
1469 }
1470 
1471 
1473 {
1474  // Changing parents probably doesn't make much sense,
1475  // but what about the names?
1476  name() = dict.name();
1477 
1479  hashedEntries_.transfer(dict.hashedEntries_);
1480  patternEntries_.transfer(dict.patternEntries_);
1481  patternRegexps_.transfer(dict.patternRegexps_);
1482 }
1483 
1484 
1485 // * * * * * * * * * * * * * * * Member Operators * * * * * * * * * * * * * //
1486 
1488 {
1489  return lookup(keyword);
1490 }
1491 
1492 
1494 {
1495  // Check for assignment to self
1496  if (this == &rhs)
1497  {
1498  FatalIOErrorInFunction(*this)
1499  << "attempted assignment to self for dictionary " << name()
1500  << abort(FatalIOError);
1501  }
1502 
1503  name() = rhs.name();
1504  clear();
1505 
1506  // Create clones of the entries in the given dictionary
1507  // resetting the parentDict to this dictionary
1508 
1509  forAllConstIter(IDLList<entry>, rhs, iter)
1510  {
1511  add(iter().clone(*this).ptr());
1512  }
1513 }
1514 
1515 
1517 {
1518  // Check for assignment to self
1519  if (this == &rhs)
1520  {
1521  FatalIOErrorInFunction(*this)
1522  << "attempted assignment to self for dictionary " << name()
1523  << abort(FatalIOError);
1524  }
1525 
1526  dictionaryName::operator=(move(rhs));
1527  IDLList<entry>::operator=(move(rhs));
1528  hashedEntries_ = move(rhs.hashedEntries_);
1529  patternEntries_ = move(rhs.patternEntries_);
1530  patternRegexps_ = move(rhs.patternRegexps_);
1531 }
1532 
1533 
1535 {
1536  // Check for assignment to self
1537  if (this == &rhs)
1538  {
1539  FatalIOErrorInFunction(*this)
1540  << "attempted addition assignment to self for dictionary " << name()
1541  << abort(FatalIOError);
1542  }
1543 
1544  forAllConstIter(IDLList<entry>, rhs, iter)
1545  {
1546  add(iter().clone(*this).ptr());
1547  }
1548 }
1549 
1550 
1552 {
1553  // Check for assignment to self
1554  if (this == &rhs)
1555  {
1556  FatalIOErrorInFunction(*this)
1557  << "attempted assignment to self for dictionary " << name()
1558  << abort(FatalIOError);
1559  }
1560 
1561  forAllConstIter(IDLList<entry>, rhs, iter)
1562  {
1563  if (!found(iter().keyword()))
1564  {
1565  add(iter().clone(*this).ptr());
1566  }
1567  }
1568 }
1569 
1570 
1572 {
1573  // Check for assignment to self
1574  if (this == &rhs)
1575  {
1576  FatalIOErrorInFunction(*this)
1577  << "attempted assignment to self for dictionary " << name()
1578  << abort(FatalIOError);
1579  }
1580 
1581  forAllConstIter(IDLList<entry>, rhs, iter)
1582  {
1583  set(iter().clone(*this).ptr());
1584  }
1585 }
1586 
1587 
1588 /* * * * * * * * * * * * * * * * Global operators * * * * * * * * * * * * * */
1589 
1590 Foam::dictionary Foam::operator+
1592  const dictionary& dict1,
1593  const dictionary& dict2
1594 )
1595 {
1596  dictionary sum(dict1);
1597  sum += dict2;
1598  return sum;
1599 }
1600 
1601 
1602 Foam::dictionary Foam::operator|
1604  const dictionary& dict1,
1605  const dictionary& dict2
1606 )
1607 {
1608  dictionary sum(dict1);
1609  sum |= dict2;
1610  return sum;
1611 }
1612 
1613 
1614 // * * * * * * * * * * * * * * * Global Functions * * * * * * * * * * * * * //
1615 
1616 void Foam::dictArgList
1618  const string& funcArgs,
1619  word& funcName,
1620  wordReList& args,
1621  List<Tuple2<word, string>>& namedArgs
1622 )
1623 {
1624  funcName = funcArgs;
1625 
1626  int argLevel = 0;
1627  bool namedArg = false;
1628  word argName;
1629 
1630  word::size_type start = 0;
1631  word::size_type i = 0;
1632 
1633  for
1634  (
1635  word::const_iterator iter = funcArgs.begin();
1636  iter != funcArgs.end();
1637  ++iter
1638  )
1639  {
1640  char c = *iter;
1641 
1642  if (c == '(')
1643  {
1644  if (argLevel == 0)
1645  {
1646  funcName = funcArgs(start, i - start);
1647  start = i+1;
1648  }
1649  ++argLevel;
1650  }
1651  else if (c == ',' || c == ')')
1652  {
1653  if (argLevel == 1)
1654  {
1655  if (namedArg)
1656  {
1657  namedArgs.append
1658  (
1660  (
1661  argName,
1662  funcArgs(start, i - start)
1663  )
1664  );
1665  namedArg = false;
1666  }
1667  else
1668  {
1669  args.append(wordRe(funcArgs(start, i - start)));
1670  }
1671  start = i+1;
1672  }
1673 
1674  if (c == ')')
1675  {
1676  if (argLevel == 1)
1677  {
1678  break;
1679  }
1680  --argLevel;
1681  }
1682  }
1683  else if (c == '=')
1684  {
1685  argName = funcArgs(start, i - start);
1686  string::stripInvalid<variable>(argName);
1687  start = i+1;
1688  namedArg = true;
1689  }
1690 
1691  ++i;
1692  }
1693 
1694  // Strip whitespace from the function name
1695  string::stripInvalid<word>(funcName);
1696 }
1697 
1698 
1699 void Foam::dictArgList
1701  const string& funcArgs,
1702  wordReList& args,
1703  List<Tuple2<word, string>>& namedArgs
1704 )
1705 {
1706  int argLevel = 0;
1707  bool namedArg = false;
1708  word argName;
1709 
1710  word::size_type start = 0;
1711  word::size_type i = 0;
1712 
1713  for
1714  (
1715  word::const_iterator iter = funcArgs.begin();
1716  iter != funcArgs.end();
1717  ++iter
1718  )
1719  {
1720  char c = *iter;
1721 
1722  if (c == '(')
1723  {
1724  ++argLevel;
1725  }
1726  else if (c == ',' || std::next(iter) == funcArgs.end())
1727  {
1728  if (std::next(iter) == funcArgs.end())
1729  {
1730  if (c == ')')
1731  {
1732  --argLevel;
1733  }
1734 
1735  ++i;
1736  }
1737 
1738  if (argLevel == 0)
1739  {
1740  if (namedArg)
1741  {
1742  namedArgs.append
1743  (
1745  (
1746  argName,
1747  funcArgs(start, i - start)
1748  )
1749  );
1750  namedArg = false;
1751  }
1752  else
1753  {
1754  args.append(wordRe(funcArgs(start, i - start)));
1755  }
1756  start = i+1;
1757  }
1758  }
1759  else if (c == '=')
1760  {
1761  argName = funcArgs(start, i - start);
1762  string::stripInvalid<variable>(argName);
1763  start = i+1;
1764  namedArg = true;
1765  }
1766  else if (c == ')')
1767  {
1768  --argLevel;
1769  }
1770 
1771  ++i;
1772  }
1773 }
1774 
1775 
1777 {
1778  string::size_type i = scopedName.find_last_of
1779  (
1781  );
1782 
1783  if (i != string::npos)
1784  {
1785  return Pair<word>
1786  (
1787  scopedName.substr(0, i),
1788  scopedName.substr(i+1, string::npos)
1789  );
1790  }
1791  else
1792  {
1793  return Pair<word>("", scopedName);
1794  }
1795 }
1796 
1797 
1798 // ************************************************************************* //
static bool slash()
Return true if the inputSyntax is slash.
Template class for intrusive linked lists.
Definition: ILList.H:50
void write(Ostream &, const bool subDict=true) const
Write dictionary, normally with sub-dictionary formatting.
Definition: dictionaryIO.C:207
A class for handling keywords in dictionaries.
Definition: keyType.H:66
virtual autoPtr< entry > clone(const dictionary &parentDict) const =0
Construct on freestore as copy with reference to the.
dictionary dict
bool found(const word &, bool recursive=false, bool patternMatch=true) const
Search dictionary for given keyword.
Definition: dictionary.C:643
#define forAll(list, i)
Loop across all elements in list.
Definition: UList.H:434
bool remove(const word &)
Remove an entry specified by keyword.
Definition: dictionary.C:1296
const entry & lookupEntryBackwardsCompatible(const wordList &, bool recursive, bool patternMatch) const
Find and return an entry data stream if present, trying a list.
Definition: dictionary.C:822
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
A class for handling file names.
Definition: fileName.H:79
label endLineNumber() const
Return line number of last token in dictionary.
Definition: dictionary.C:596
void operator=(const dictionary &)
Definition: dictionary.C:1493
tokenList tokens() const
Return the dictionary as a list of tokens.
Definition: dictionary.C:623
const entry * lookupEntryPtr(const word &, bool recursive, bool patternMatch) const
Find and return an entry data stream pointer if present.
Definition: dictionary.C:682
const keyType & keyword() const
Return keyword.
Definition: entry.H:123
An STL-conforming const_iterator.
Definition: HashTable.H:481
const dictionary & scopedDict(const word &) const
Find and return a sub-dictionary by scoped lookup.
Definition: dictionary.C:1057
Wrapper around POSIX extended regular expressions.
Definition: regExp.H:61
SHA1Digest digest() const
Return the SHA1 digest of the dictionary contents.
Definition: dictionary.C:609
errorManipArg< error, int > exit(error &err, const int errNo=1)
Definition: errorManip.H:124
void operator+=(const dictionary &)
Include entries from the given dictionary.
Definition: dictionary.C:1534
List< token > tokenList
List of tokens, used for a IOdictionary entry.
Definition: tokenList.H:42
A list of keyword definitions, which are a keyword followed by any number of values (e...
Definition: dictionary.H:156
A 2-tuple for storing two objects of different types.
Definition: HashTable.H:65
const entry * lookupEntryPtrBackwardsCompatible(const wordList &, bool recursive, bool patternMatch) const
Find and return an entry data stream if present, trying a list.
Definition: dictionary.C:765
void transfer(ILList< LListBase, T > &)
Transfer the contents of the argument into this List.
Definition: ILList.C:134
A 1D array of objects of type <T>, where the size of the vector is known and used for subscript bound...
Definition: HashTable.H:59
Template class for non-intrusive linked lists.
Definition: LList.H:51
#define forAllIter(Container, container, iter)
Iterate across all elements in the container object of type.
Definition: UList.H:459
dictionaryName()
Construct dictionaryName null.
Definition: dictionary.H:90
An STL-conforming const_iterator.
Definition: LList.H:297
A token holds items read from Istream.
Definition: token.H:72
static const fileName null
An empty fileName.
Definition: fileName.H:97
static bool dot()
Return true if the inputSyntax is dot.
Ostream & endl(Ostream &os)
Add newline and flush stream.
Definition: Ostream.H:251
The SHA1 message digest.
Definition: SHA1Digest.H:62
An STL-conforming iterator.
Definition: LList.H:246
virtual const dictionary & dict() const =0
Return dictionary if this entry is a dictionary.
friend class iterator
Definition: LList.H:82
static bool writeOptionalEntries
If true write optional keywords and values.
Definition: dictionary.H:246
const entry & lookupEntry(const word &, bool recursive, bool patternMatch) const
Find and return an entry data stream if present otherwise error.
Definition: dictionary.C:801
The output stream for calculating SHA1 digests.
Definition: OSHA1stream.H:133
T * last()
Return the last entry.
Definition: UILList.H:121
A keyword and a list of tokens is a &#39;dictionaryEntry&#39;.
void transfer(dictionary &)
Transfer the contents of the argument and annul the argument.
Definition: dictionary.C:1472
const dimensionedScalar c
Speed of light in a vacuum.
autoPtr< dictionary > clone() const
Construct and return clone.
Definition: dictionary.C:552
An STL-conforming const_iterator.
Definition: UILList.H:234
const entry * lookupScopedEntryPtr(const word &, bool recursive, bool patternMatch) const
Find and return an entry data stream pointer if present.
Definition: dictionary.C:871
wordList toc() const
Return the table of contents.
Definition: dictionary.C:1095
int infoSwitch(const char *name, const int defaultValue=0)
Lookup info switch or add default value.
Definition: debug.C:233
bool isDict(const word &) const
Check if entry is a sub-dictionary.
Definition: dictionary.C:936
bool add(entry *, bool mergeEntry=false)
Add a new entry.
Definition: dictionary.C:1133
dimensioned< Type > sum(const DimensionedField< Type, GeoMesh > &df)
const dictionary & subDict(const word &) const
Find and return a sub-dictionary.
Definition: dictionary.C:982
A keyword and a list of tokens is a &#39;primitiveEntry&#39;. An primitiveEntry can be read, written and printed, and the types and values of its tokens analysed.
dictionary()
Construct top-level dictionary null.
Definition: dictionary.C:440
An STL-conforming iterator.
Definition: HashTable.H:426
bool changeKeyword(const keyType &oldKeyword, const keyType &newKeyword, bool forceOverwrite=false)
Change the keyword for an entry,.
Definition: dictionary.C:1329
Pair< word > dictAndKeyword(const word &scopedName)
Extracts dict name and keyword.
Definition: dictionary.C:1776
void operator<<=(const dictionary &)
Unconditionally include entries from the given dictionary.
Definition: dictionary.C:1571
static int disableFunctionEntries
Definition: entry.H:86
An ordered pair of two objects of type <T> with first() and second() elements.
Definition: contiguous.H:49
const fileName & name() const
Return the dictionary name.
Definition: dictionary.H:109
A 1D vector of objects of type <T> that resizes itself as necessary to accept the new objects...
Definition: DynamicList.H:56
const dictionary & optionalSubDict(const word &) const
Find and return a sub-dictionary if found.
Definition: dictionary.C:1040
A class for handling words, derived from string.
Definition: word.H:59
const dictionary & parent() const
Return the parent dictionary.
Definition: dictionary.H:301
void clear()
Clear the contents of the list.
Definition: ILList.C:121
void append(const T &)
Append an element at the end of the list.
Definition: ListI.H:178
static const dictionary null
Null dictionary.
Definition: dictionary.H:242
An STL-conforming iterator.
Definition: UILList.H:185
const dictionary & topDict() const
Return the top of the tree.
Definition: dictionary.C:568
T * remove(T *p)
Remove and return element.
Definition: UILList.H:142
graph_traits< Graph >::vertices_size_type size_type
Definition: SloanRenumber.C:73
forAllConstIter(PtrDictionary< phaseModel >, mixture.phases(), phase)
Definition: pEqn.H:29
errorManip< error > abort(error &err)
Definition: errorManip.H:131
A wordRe is a word, but can also have a regular expression for matching words.
Definition: wordRe.H:74
static char scopeChar()
Return true if the inputSyntax is slash.
const dictionary * subDictPtr(const word &) const
Find and return a sub-dictionary pointer if present.
Definition: dictionary.C:952
virtual bool isDict() const
Return true if this entry is a dictionary.
Definition: entry.H:156
defineTypeNameAndDebug(combustionModel, 0)
word name(const complex &)
Return a string representation of a complex.
Definition: complex.C:47
LList< DLListBase, T > DLList
Definition: DLList.H:43
List< keyType > keys(bool patterns=false) const
Return the list of available keys or patterns.
Definition: dictionary.C:1115
friend class const_iterator
Definition: LList.H:85
void setSize(const label)
Reset size of List.
Definition: List.C:281
void operator|=(const dictionary &)
Conditionally include entries from the given dictionary.
Definition: dictionary.C:1551
ITstream & operator[](const word &) const
Find and return entry.
Definition: dictionary.C:1487
void operator=(const dictionaryName &name)
Definition: dictionary.H:140
#define FatalIOErrorInFunction(ios)
Report an error message using Foam::FatalIOError.
Definition: error.H:335
Input from memory buffer stream.
Definition: IStringStream.H:49
string str() const
Return the string.
virtual const fileName & name() const =0
Return the dictionary name.
virtual ~dictionary()
Destructor.
Definition: dictionary.C:560
void set(entry *)
Assign a new entry, overwrite any existing entry.
Definition: dictionary.C:1271
bool substituteScopedKeyword(const word &keyword)
Substitute the given scoped keyword prepended by &#39;$&#39; with the.
Definition: dictionary.C:912
bool merge(const dictionary &)
Merge entries from the given dictionary.
Definition: dictionary.C:1418
#define IOWarningInFunction(ios)
Report an IO warning using Foam::Warning.
An auto-pointer similar to the STL auto_ptr but with automatic casting to a reference to the type and...
Definition: PtrList.H:52
const doubleScalar e
Elementary charge.
Definition: doubleScalar.H:105
volScalarField & p
T * first()
Return the first entry.
Definition: UILList.H:109
void clear()
Clear the dictionary.
Definition: dictionary.C:1463
virtual ITstream & stream() const =0
Return token stream if this entry is a primitive entry.
void operator=(const ILList< LListBase, T > &)
Assignment operator.
Definition: ILList.C:144
A class for handling character strings derived from std::string.
Definition: string.H:76
Output to memory buffer stream.
Definition: OStringStream.H:49
label startLineNumber() const
Return line number of first token in dictionary.
Definition: dictionary.C:583
void dictArgList(const string &funcArgs, word &funcName, wordReList &args, List< Tuple2< word, string >> &namedArgs)
Parse dictionary substitution argument list.
Definition: dictionary.C:1617
wordList sortedToc() const
Return the sorted table of contents.
Definition: dictionary.C:1109
Input token stream.
Definition: ITstream.H:49
dictionary subOrEmptyDict(const word &, const bool mustRead=false) const
Find and return a sub-dictionary as a copy, or.
Definition: dictionary.C:1013
ITstream & lookupBackwardsCompatible(const wordList &, bool recursive=false, bool patternMatch=true) const
Find and return an entry data stream, trying a list of keywords.
Definition: dictionary.C:855
Foam::SHA1Digest digest()
Return SHA1::Digest for the data processed until now.
Definition: OSHA1stream.H:178
Namespace for OpenFOAM.
A keyword and a list of tokens is an &#39;entry&#39;.
Definition: entry.H:65
bool isPattern() const
Should be treated as a match rather than a literal string.
Definition: keyTypeI.H:97
ITstream & lookup(const word &, bool recursive=false, bool patternMatch=true) const
Find and return an entry data stream.
Definition: dictionary.C:844
IOerror FatalIOError