Loading...
Searching...
No Matches
ABAQUSCore.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) 2020-2022 OpenCFD Ltd.
9-------------------------------------------------------------------------------
10License
11 This file is part of OpenFOAM.
12
13 OpenFOAM is free software: you can redistribute it and/or modify it
14 under the terms of the GNU General Public License as published by
15 the Free Software Foundation, either version 3 of the License, or
16 (at your option) any later version.
17
18 OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
19 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
20 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
21 for more details.
22
23 You should have received a copy of the GNU General Public License
24 along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
25
26\*---------------------------------------------------------------------------*/
27
28#include "ABAQUSCore.H"
29#include "IFstream.H"
30#include "ListOps.H"
31#include "stringOps.H"
32#include "SpanStream.H"
33#include "cellModel.H"
34#include <cctype>
35
36// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
37
39
40
41// * * * * * * * * * * * * * * * Local Functions * * * * * * * * * * * * * * //
42
43namespace Foam
44{
46// Use peek(), get(), unget() to detect and skip lines that appear to be
47// "** comment" lines.
48//
49// Uses a mix of std::istream and ISstream methods
50// since we need the low-level get()/unget()
51
52static void skipComments(ISstream& iss)
53{
54 #if OPENFOAM < 2002
55 string line;
56 #endif
57
58 auto& is = iss.stdStream();
59
60 bool isComment = true;
61 while (isComment)
62 {
63 isComment = ('*' == is.peek());
64
65 if (isComment)
66 {
67 // Get and check the next one
68 (void) is.get();
69
70 isComment = ('*' == is.peek());
71 if (isComment)
72 {
73 // Found "** ..." (a comment) - read/discard
74 // ISstream::getLine to keep track of the line numbers
75
76 #if OPENFOAM >= 2002
77 iss.getLine(nullptr);
78 #else
79 iss.getLine(line);
80 #endif
81 }
82 else
83 {
84 // Not a comment
85 // - unget the '*', implicitly break out of loop
86 is.unget();
87 }
88 }
89 }
90
91 iss.syncState();
92}
93
94
95// Get an identifier of the form "NSET=..." (case-insensitive)
96// Return the string on success, an empty string on failure
97
98static string getIdentifier(const word& keyword, string& inputLine)
99{
100 // Strip out whitespace (not a valid Abaqus identifier anyhow)
101 // - makes parsing easier, avoids tab/carriage-returns etc.
102
104
105 // Do string comparisons in upper-case
106
107 const auto key(stringOps::upper(keyword));
108 const auto line(stringOps::upper(inputLine));
109
110 // Extract "..,key=value,key2=value,"
111
112 // Not sure if we need the additional ',' prefix
113 // in search to avoid similar keys.
114
115 auto beg = line.find("," + key + "=");
116
117 if (beg != std::string::npos)
118 {
119 // Skip past the '='
120 beg += key.size() + 2;
121
122 // The closing comma
123 auto len = line.find(',', beg);
124 if (len != std::string::npos)
125 {
126 len -= beg;
127 }
128
129 // Substring from inputLine (not uppercase!)
130 return inputLine.substr(beg, len);
131 }
132
133 // Not found
134 return string();
135}
136
138// Walk the string content (CSV format) to append integer labels
139// until the line is exhausted or the list is full.
140//
141// Return false on read error or if the line exhausted while getting
142// element.
143
144static bool appendCsvLabels
145(
146 const std::string& line,
147 labelUList& elemNodes,
148 label& nodei
149)
150{
151 const label nNodes = elemNodes.size();
152
153 std::size_t pos = 0;
154
155 while (nodei < nNodes && pos != std::string::npos)
156 {
157 auto beg = pos;
158 auto len = line.find(',', pos);
159
160 if (len == std::string::npos)
161 {
162 pos = len;
163 }
164 else
165 {
166 pos = len + 1;
167 len -= beg;
168 }
169
170 if (readLabel(line.substr(beg, len), elemNodes[nodei]))
171 {
172 ++nodei;
173 }
174 else
175 {
176 // Read error, or need another line
177 return false;
178 }
179 }
180
181 return (nodei >= nNodes);
182}
183
185} // End namespace Foam
186
187
188// * * * * * * * * * * * * * Static Member Functions * * * * * * * * * * * * //
189
192{
193 if (abaqusToFoamFaceAddr_.empty())
194 {
195 abaqusToFoamFaceAddr_.emplace(abaqusTet, labelList({3, 2, 0, 1}));
196 abaqusToFoamFaceAddr_.emplace(abaqusPrism, labelList({0, 1, 4, 3, 2}));
197 abaqusToFoamFaceAddr_.emplace(abaqusHex, labelList({4, 5, 2, 1, 3, 0}));
199
201}
202
203
205Foam::fileFormats::ABAQUSCore::getElementType(const string& elemTypeName)
206{
207 // Check for element-type.
208 #undef checkElemType
209 #define checkElemType(Name) elemTypeName.contains(Name)
210
211 if
212 (
213 checkElemType("S3")
214 || checkElemType("CPE3")
215 || checkElemType("2D3")
216 )
217 {
218 return shapeType::abaqusTria;
219 }
220 else if
221 (
222 checkElemType("S4")
223 || checkElemType("CPE4")
224 || checkElemType("2D4")
225 || checkElemType("CPEG4")
226 )
227 {
228 return shapeType::abaqusQuad;
229 }
230 else if
231 (
232 checkElemType("3D4") // C3D4*, Q3D4, ...
233 )
234 {
235 return shapeType::abaqusTet;
236 }
237 else if
238 (
239 checkElemType("3D5") // C3D5*
240 )
241 {
242 return shapeType::abaqusPyr;
243 }
244 else if
245 (
246 checkElemType("3D6") // C3D6*
247 )
248 {
249 return shapeType::abaqusPrism;
250 }
251 else if
252 (
253 checkElemType("3D8") // C3D8*
254 )
255 {
256 return shapeType::abaqusHex;
257 }
258
259 #undef checkElemType
260
262}
263
264
265// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
266
267Foam::label
269(
270 const std::string& setName
271)
272{
273 if (elsetMap_.empty())
274 {
275 // Always have a lookup for empty string
276 elsetMap_.set(string::null, 0);
277 }
278
279 if (setName.empty())
280 {
281 return 0;
282 }
283
284 // Direct case-sensitive lookup - it might be there
285
286 label setId = elsetMap_.lookup(setName, -1);
287 if (setId >= 0)
288 {
289 return setId;
290 }
291
292
293 // Case-insensitive search, use upper-case
294
295 const auto needle(stringOps::upper(setName));
296
297 forAllConstIters(elsetMap_, iter)
298 {
299 const auto haystack(stringOps::upper(iter.key()));
300
301 if (needle == haystack)
302 {
303 return iter.val();
304 }
305 }
306
307 // Not there. Save at the next location
308 setId = elsetMap_.size();
309 elsetMap_.set(setName, setId);
310
311 return setId;
312}
313
314
315Foam::label
317(
318 ISstream& is
319)
320{
321 const label initialCount = points_.size();
322
323 char sep; // Comma separator (dummy)
324 string line;
325 label id;
326 point p;
327
328 // Read nodes (points) until next "*Section"
329 while (is.peek() != '*' && is.peek() != EOF)
330 {
331 // Grab the line and wrap as spanstream
332 is.getLine(line);
333
334 if (line.empty())
335 {
336 // Not sure if we should terminate on blank lines?
337 continue;
338 }
339 ISpanStream ss(line);
340
341 // Parse line for ID, X, Y, Z
342 ss >> id >> sep >> p.x() >> sep >> p.y() >> sep >> p.z();
343
344 nodeIds_.append(id);
345 points_.append(p);
347
348 return (points_.size() - initialCount);
349}
350
351
352Foam::label
354(
355 ISstream& is,
356 const ABAQUSCore::shapeType shape,
357 const label setId
358)
359{
360 // Info<< "*Element" << nl;
361
362 const label nNodes = ABAQUSCore::nPoints(shape);
363
364 if (!nNodes)
365 {
366 return 0;
367 }
368
369 const label initialCount = elemTypes_.size();
370
371 char sep; // Comma separator (dummy)
372 string line;
373 label id;
374
375 labelList elemNodes(nNodes, Zero);
376
377 // Read element connectivity until next "*Section"
378
379 // Parse for ID, node1, node2, ...
380 while (is.peek() != '*' && is.peek() != EOF)
381 {
382 // elemNodes = Zero; for sanity checks?
383
384 is >> id >> sep;
385
386 label nodei = 0;
387 while (nodei < nNodes)
388 {
389 // Grab the rest of the line, walk through CSV fields
390 is.getLine(line);
391
392 appendCsvLabels(line, elemNodes, nodei);
393 }
394
395 // Checks?
396
397 connectivity_.append(elemNodes);
398 elemTypes_.append(shape);
399 elemIds_.append(id);
400 elsetIds_.append(setId);
402
403 return (elemTypes_.size() - initialCount);
404}
405
406
407Foam::label
409(
410 ISstream& is,
411 const label setId
412)
413{
414 // Info<< "*Surface" << nl;
415
416 // Models for supported solids (need to face mapping)
420
421 // Face mapping from Abaqus cellModel to OpenFOAM cellModel
422 const auto& abqToFoamFaceMap = abaqusToFoamFaceAddr();
423
424 const label initialCount = elemTypes_.size();
425
426 char sep; // Comma separator (dummy)
427 string line;
428 label id;
429
430 // Read until next "*Section"
431
432 // Parse for elemId, sideId.
433 // Eg, "1235, S1"
434 while (is.peek() != '*' && is.peek() != EOF)
435 {
436 is >> id >> sep;
437 is.getLine(line);
438
439 const word sideName(word::validate(stringOps::upper(line)));
440
441 if
442 (
443 sideName.size() != 2
444 || sideName[0] != 'S'
445 || !std::isdigit(sideName[1])
446 )
447 {
448 Info<< "Abaqus reader: unsupported surface element side "
449 << id << ", " << sideName << nl;
450 continue;
451 }
452
453 const label index = elemIds_.find(id);
454 if (id <= 0 || index < 0)
455 {
456 Info<< "Abaqus reader: unsupported surface element "
457 << id << nl;
458 continue;
459 }
460
461 const auto faceIdIter = abqToFoamFaceMap.cfind(elemTypes_[index]);
462 if (!faceIdIter.good())
463 {
464 Info<< "Abaqus reader: reject non-solid shape: " << nl;
465 }
466
467 // The abaqus element side number (1-based)
468 const label sideNum = (sideName[1] - '0');
469
470 const label foamFaceNum = (*faceIdIter)[sideNum - 1];
471
472 const labelList& connect = connectivity_[index];
473
474 // Nodes for the derived shell element
475 labelList elemNodes;
476
477 switch (elemTypes_[index])
478 {
479 case shapeType::abaqusTet:
480 {
481 elemNodes = labelList(connect, tet.modelFaces()[foamFaceNum]);
482 break;
483 }
484 case shapeType::abaqusPrism:
485 {
486 elemNodes = labelList(connect, prism.modelFaces()[foamFaceNum]);
487 break;
488 }
489 case shapeType::abaqusHex:
490 {
491 elemNodes = labelList(connect, hex.modelFaces()[foamFaceNum]);
492 break;
493 }
494 default:
495 break;
496 }
497
498 enum shapeType shape = shapeType::abaqusUnknownShape;
499
500 if (elemNodes.size() == 3)
501 {
502 shape = shapeType::abaqusTria;
503 }
504 else if (elemNodes.size() == 4)
505 {
506 shape = shapeType::abaqusQuad;
507 }
508 else
509 {
510 // Cannot happen
512 << "Could not map face side for "
513 << id << ", " << sideName << nl
514 << exit(FatalError);
515 }
516
517 // Synthesize face Id from solid element Id and side Id
518 const label newElemId = ABAQUSCore::encodeSolidId(id, sideNum);
519
520 // Further checks?
521 connectivity_.append(std::move(elemNodes));
522 elemTypes_.append(shape);
523 elemIds_.append(newElemId);
524 elsetIds_.append(setId);
525 }
526
527 return (elemTypes_.size() - initialCount);
528}
529
530
532(
533 ISstream& is
534)
535{
536 clear();
537
538 label nread;
539 string line;
540
541 while (is.good())
542 {
543 is.getLine(line);
544
545 // Start processing on "*Section-Name",
546 // but skip "** comments" etc
547 if (line[0] != '*' || !std::isalpha(line[1]))
548 {
549 continue;
550 }
551
552 // Some abaqus files use upper-case or mixed-case for section names,
553 // convert all to upper-case for ease.
554
555 const string upperLine(stringOps::upper(line));
556
557 //
558 // "*Nodes" section
559 //
560 if (upperLine.starts_with("*NODE"))
561 {
562 // Ignore "NSET=...", we cannot do anything useful with it
563
564 skipComments(is);
565
566 nread = readPoints(is);
567
568 if (verbose_)
569 {
570 InfoErr
571 << "Read " << nread << " *NODE entries" << nl;
572 }
573 continue;
574 }
575
576 //
577 // "*Element" section
578 //
579 if (upperLine.starts_with("*ELEMENT,"))
580 {
581 // Must have "TYPE=..."
582 const string elemTypeName(getIdentifier("TYPE", line));
583
584 // May have "ELSET=..." on the same line
585 const string elsetName(getIdentifier("ELSET", line));
586
587 const shapeType shape(getElementType(elemTypeName));
588
589 if (!ABAQUSCore::nPoints(shape))
590 {
591 // Unknown/unsupported
592 if (verbose_)
593 {
594 InfoErr
595 << "Ignore abaqus element type: "
596 << elemTypeName << nl;
597 }
598 continue;
599 }
600
601 const label elsetId = addNewElset(elsetName);
602
603 skipComments(is);
604
605 nread = readElements(is, shape, elsetId);
606
607 if (verbose_)
608 {
609 InfoErr
610 << "Read " << nread << " *ELEMENT entries ("
611 << elemTypeName << ") elset="
612 << elsetName << nl;
613 }
614 continue;
615 }
616
617 //
618 // "*Surface" section
619 //
620 if (upperLine.starts_with("*SURFACE,"))
621 {
622 // Require "NAME=..." on the same line
623 const string elsetName(getIdentifier("NAME", line));
624
625 // May have "TYPE=..." on the same line.
626 // If missing, default is ELEMENT.
627 const string surfTypeName(getIdentifier("TYPE", line));
628
629 if
630 (
631 !surfTypeName.empty()
632 && stringOps::upper(surfTypeName) != "ELEMENT"
633 )
634 {
635 Info<< "Reading abaqus surface type "
636 << surfTypeName << " is not implemented" << nl;
637 continue;
638 }
639
640 // Treat like an element set
641 const label elsetId = addNewElset(elsetName);
642
643 skipComments(is);
644
645 nread = readSurfaceElements(is, elsetId);
646
647 if (verbose_)
648 {
649 InfoErr
650 << "Read " << nread << " *SURFACE entries for "
651 << elsetName << nl;
653 continue;
654 }
655 }
656}
657
658
660{
661 // Negative set
662 bitSet select(elemTypes_.size(), false);
663
664 forAll(elemTypes_, i)
665 {
666 if (!isValidType(elemTypes_[i]) || isSolidType(elemTypes_[i]))
667 {
668 select.set(i);
669 }
670 }
671
672 if (select.any())
673 {
674 select.flip();
675
676 inplaceSubset(select, connectivity_);
677 inplaceSubset(select, elemTypes_);
679 inplaceSubset(select, elemIds_);
680 inplaceSubset(select, elsetIds_);
681 }
682}
683
684
686{
687 if (!nodeIds_.empty())
688 {
689 // Has original 1-based ids
690 //
691 // Need to convert to local (0-based) points
692 // in the order in which we read them
693 // and compact unused values
694
695 // Could construct a sort order to preserve the original
696 // point order, but that is not likely relevant for anyone.
697
698
699 // Which original node ids actually being used by elements?
700
701 // We may have many ids, but speculate that they are sparse
702 // and have high element numbers.
703
704 // Use a Map instead of labelList.
705
706 Map<label> nodeIdRemapping(2*points_.size());
707
708 // Pass 1: which nodes are being used?
709
710 for (const labelList& elem : connectivity_)
711 {
712 for (const label origId : elem)
713 {
714 nodeIdRemapping(origId) = 0; // any value
715 }
716 }
717
718 // Define compact local points, finalize the node id remapping
719
720 label nPoints = 0;
721 labelList oldToNewLocal(nodeIds_.size(), -1);
722
723 forAll(nodeIds_, i)
724 {
725 const label origId = nodeIds_[i];
726
727 if (nodeIdRemapping.found(origId))
728 {
729 oldToNewLocal[i] = nPoints;
730 nodeIdRemapping(origId) = nPoints;
731 ++nPoints;
732 }
733 }
734
735 // Prune out -1 values (shrinks list)
736 inplaceReorder(oldToNewLocal, points_, true);
737
738 // Relabel the elements
739
740 for (labelList& elem : connectivity_)
741 {
742 for (label& id : elem)
743 {
744 id = nodeIdRemapping[id];
745 }
746 }
747
748 // Done!
749 nodeIds_.clear();
750 }
751 else
752 {
753 // Already numbered (0-based), but perhaps not compacted
754
755 // Which node ids actually being used by elements?
756 bitSet usedNodeIds(points_.size());
757
758 for (const labelList& elem : connectivity_)
759 {
760 usedNodeIds.set(elem);
761 }
762
763 // Compact the numbers
764 labelList oldToNewLocal = invert(points_.size(), usedNodeIds);
765
766 // Prune out -1 values (shrinks list)
767 inplaceReorder(oldToNewLocal, points_, true);
768
769
770 // Renumber non-compact to compact
771 for (labelList& elem : connectivity_)
773 inplaceRenumber(oldToNewLocal, elem);
774 }
775 }
776}
777
778
780{
781 for (label& elemId : elemIds_)
782 {
783 renumber0_elemId(elemId);
784 }
785}
786
787
789(
790 Ostream& os,
791 const UList<point>& points,
792 const scalar scaleFactor
793)
794{
795 if (points.empty())
796 {
797 return;
798 }
799
800 // Set the precision of the points data to 10
801 os.precision(10);
802
803 // Force decimal point for Fortran input
804 os.setf(std::ios::showpoint);
805
806 label vertId = 1; // 1-based vertex labels
807
808 os << "*NODE" << nl;
809 for (const point& p : points)
810 {
811 // Convert [m] -> [mm] etc
812 os << " "
813 << vertId << ", "
814 << (scaleFactor * p.x()) << ','
815 << (scaleFactor * p.y()) << ','
816 << (scaleFactor * p.z()) << nl;
817
818 ++vertId;
819 }
820}
821
822
824(
825 const UList<point>& points,
826 const UList<face>& faces,
827 labelList& decompOffsets,
828 DynamicList<face>& decompFaces
829)
830{
831 // On-demand face decomposition (triangulation)
832
833 decompOffsets.resize(faces.size()+1);
834 decompFaces.clear();
835
836 auto offsetIter = decompOffsets.begin();
837 *offsetIter = 0; // The first offset is always zero
838
839 for (const face& f : faces)
840 {
841 const label n = f.size();
842
843 if (n != 3 && n != 4)
844 {
845 // Decompose non-tri/quad into tris
846 f.triangles(points, decompFaces);
847 }
848
849 // The end offset, which is the next begin offset
850 *(++offsetIter) = decompFaces.size();
851 }
852
853 return decompFaces.size();
854}
855
856
857// ************************************************************************* //
static Foam::Map< Foam::labelList > abaqusToFoamFaceAddr_
Definition ABAQUSCore.C:31
#define checkElemType(Name)
Various functions to operate on Lists.
Input/output streams with (internal or external) character storage.
label n
A 1D vector of objects of type <T> that resizes itself as necessary to accept the new objects.
Definition DynamicList.H:68
void clear() noexcept
Clear the addressed list, i.e. set the size to zero.
bool found(const Key &key) const
Same as contains().
Definition HashTable.H:1370
bool good() const noexcept
True if next operation might succeed.
Definition IOstream.H:281
Similar to IStringStream but using an externally managed buffer for its input. This allows the input ...
Generic input stream using a standard (STL) stream.
Definition ISstream.H:54
int peek()
Raw, low-level peek function.
Definition ISstreamI.H:63
ISstream & getLine(std::string &str, char delim='\n')
Raw, low-level getline (until delimiter) into a string.
Definition ISstreamI.H:69
void syncState()
Set stream state to match that of the std::istream.
Definition ISstream.H:195
virtual const std::istream & stdStream() const
Const access to underlying std::istream.
Definition ISstream.H:163
bool set(const label i, bool val=true)
A bitSet::set() method for a list of bool.
Definition List.H:469
void resize(const label len)
Adjust allocated size of list.
Definition ListI.H:153
A HashTable to objects of type <T> with a label key.
Definition Map.H:54
An Ostream is an abstract base class for all output systems (streams, files, token lists,...
Definition Ostream.H:59
A 1D vector of objects of type <T>, where the size of the vector is known and can be used for subscri...
Definition UList.H:89
bool any() const
True if any entries are 'true'.
Definition UList.H:821
iterator begin() noexcept
Return an iterator to begin traversing the UList.
Definition UListI.H:410
void size(const label n)
Older name for setAddressableSize.
Definition UList.H:118
A bitSet stores bits (elements with only two states) in packed internal format and supports a variety...
Definition bitSet.H:61
void set(const bitSet &bitset)
Set specified bits from another bitset.
Definition bitSetI.H:502
Maps a geometry to a set of cell primitives.
Definition cellModel.H:73
const faceList & modelFaces() const noexcept
Return a raw list of model faces.
Definition cellModelI.H:60
static const cellModel & ref(const modelType model)
Look up reference to cellModel by enumeration. Fatal on failure.
Definition cellModels.C:150
A face is a list of labels corresponding to mesh vertices.
Definition face.H:71
static bool isValidType(shapeType tag)
True if element type is not unknown/invalid.
Definition ABAQUSCore.H:281
static shapeType getElementType(const string &elemTypeName)
Classify named element type (eg, S4R) to known/supported element types.
Definition ABAQUSCore.C:198
static void renumber0_elemId(label &elemId)
From 1-based to 0-based.
Definition ABAQUSCore.H:353
static int nPoints(shapeType tag)
The number of points associated with the element type.
Definition ABAQUSCore.H:273
static const Map< labelList > & abaqusToFoamFaceAddr()
Face addressing from ABAQUS faces to OpenFOAM faces.
Definition ABAQUSCore.C:184
static label encodeSolidId(const label id, const label side)
Combine solid element Id and side Id into synthetic face Id.
Definition ABAQUSCore.H:313
static void writePoints(Ostream &os, const UList< point > &points, const scalar scaleFactor=1.0)
Write '*NODE' header and entries to file, optionally with scaling.
Definition ABAQUSCore.C:782
static bool isSolidType(shapeType tag)
True if element type is a 3D element.
Definition ABAQUSCore.H:297
static label faceDecomposition(const UList< point > &points, const UList< face > &faces, labelList &decompOffsets, DynamicList< face > &decompFaces)
Calculate face decomposition for non tri/quad faces.
Definition ABAQUSCore.C:817
shapeType
Shape-Type - the values are for internal use only!
Definition ABAQUSCore.H:249
A line primitive.
Definition line.H:180
A class for handling character strings derived from std::string.
Definition string.H:76
static const string null
An empty string.
Definition string.H:203
bool starts_with(char c) const
True if string starts with given character (cf. C++20).
Definition string.H:436
A class for handling words, derived from Foam::string.
Definition word.H:66
static word validate(const std::string &s, const bool prefix=false)
Construct validated word (no invalid characters).
Definition word.C:39
volScalarField & p
#define FatalErrorInFunction
Report an error message using Foam::FatalError.
Definition error.H:600
OBJstream os(runTime.globalPath()/outputName)
const pointField & points
label nPoints
surface1 clear()
List< bool > select(const label n, const labelUList &locations)
Construct a selection list of bools (all false) with the given pre-size, subsequently add specified l...
Definition BitOps.C:139
string upper(const std::string &s)
Return string copy transformed with std::toupper on each character.
void inplaceRemoveSpace(std::string &s)
Eliminate whitespace inplace.
Namespace for OpenFOAM.
dimensionedScalar pos(const dimensionedScalar &ds)
void inplaceSubset(const BoolListType &select, ListType &input, const bool invert=false)
Inplace extract elements of the input list when select is true.
void inplaceRenumber(const labelUList &oldToNew, IntListType &input)
Inplace renumber the values within a list.
static void skipComments(ISstream &iss)
Definition ABAQUSCore.C:45
List< label > labelList
A List of labels.
Definition List.H:62
label readLabel(const char *buf)
Parse entire buffer as a label, skipping leading/trailing whitespace.
Definition label.H:63
messageStream Info
Information stream (stdout output on master, null elsewhere).
IOstream & hex(IOstream &io)
Definition IOstream.H:579
static string getIdentifier(const word &keyword, string &inputLine)
Definition ABAQUSCore.C:91
void inplaceReorder(const labelUList &oldToNew, ListType &input, const bool prune=false)
Inplace reorder the elements of a list.
static bool appendCsvLabels(const std::string &line, labelUList &elemNodes, label &nodei)
Definition ABAQUSCore.C:138
vector point
Point is a vector.
Definition point.H:37
static constexpr const zero Zero
Global zero (0).
Definition zero.H:127
messageStream InfoErr
Information stream (stderr output on master, null elsewhere).
error FatalError
Error stream (stdout output on all processes), with additional 'FOAM FATAL ERROR' header text and sta...
labelList invert(const label len, const labelUList &map)
Create an inverse one-to-one mapping.
Definition ListOps.C:28
errorManipArg< error, int > exit(error &err, const int errNo=1)
Definition errorManip.H:125
UList< label > labelUList
A UList of labels.
Definition UList.H:75
constexpr char nl
The newline '\n' character (0x0a).
Definition Ostream.H:50
labelList f(nPoints)
#define forAll(list, i)
Loop across all elements in list.
Definition stdFoam.H:299
#define forAllConstIters(container, iter)
Iterate across all elements of the container object with const access.
Definition stdFoam.H:235
DynamicList< label > elemIds_
The 1-based abaqus Id for the element.
Definition ABAQUSCore.H:417
label readPoints(ISstream &is)
Read entries within a "*Nodes" section.
Definition ABAQUSCore.C:310
DynamicList< point > points_
Locations of the points (nodes).
Definition ABAQUSCore.H:396
HashTable< label, string > elsetMap_
Mapping of elem set names.
Definition ABAQUSCore.H:432
void renumber_elements_1to0()
Renumber elements from 1-based to 0-based.
Definition ABAQUSCore.C:772
void read(ISstream &is)
Read an abaqus input file.
Definition ABAQUSCore.C:525
bool verbose_
Additional verbosity.
Definition ABAQUSCore.H:388
DynamicList< label > nodeIds_
The 1-based abaqus Id for the point (node).
Definition ABAQUSCore.H:401
DynamicList< labelList > connectivity_
The element connectivity.
Definition ABAQUSCore.H:412
label readElements(ISstream &is, const ABAQUSCore::shapeType shape, const label setId=0)
Read entries within an "*Element" section.
Definition ABAQUSCore.C:347
void purge_solids()
Remove non-shell elements and compact the points.
Definition ABAQUSCore.C:652
label readSurfaceElements(ISstream &is, const label setId=0)
Read elements within an "*Surface" section.
Definition ABAQUSCore.C:402
label addNewElset(const std::string &setName)
Add a new element set name or return an existing one.
Definition ABAQUSCore.C:262
DynamicList< label > elsetIds_
The element set ids.
Definition ABAQUSCore.H:427
void compact_nodes()
Compact unused points and relabel connectivity.
Definition ABAQUSCore.C:678
DynamicList< ABAQUSCore::shapeType > elemTypes_
The element types.
Definition ABAQUSCore.H:422