File tree Expand file tree Collapse file tree
ifcopenshell-python/ifcopenshell/geom Expand file tree Collapse file tree Original file line number Diff line number Diff line change @@ -138,6 +138,8 @@ class StatsCollector:
138138
139139 counters : list
140140
141+ num_semis : int = 0
142+
141143 def __init__ (self ):
142144 self .streamer = ifcopenshell_wrapper .InstanceStreamer ()
143145 self .needs_data = True
@@ -151,17 +153,19 @@ def feedFromFile(self, f: Optional[IO[str]] = None):
151153 def feed (self , data : str ):
152154 self .streamer .pushPage (data )
153155 self .needs_data = False
156+ self .num_semis = self .streamer .semicolonCount ()
154157
155158 @staticmethod
156- def fromFilePath (fn , page_size : int = 4096 ):
159+ def fromFilePath (fn , page_size : int = 102400 ):
157160 collector = StatsCollector ()
158161 collector .page_size = page_size
159162 collector .feedFromFile (open (str (fn ), encoding = "ascii" ))
160163 return collector
161164
162165 def next (self ):
163- if self .streamer . hasSemicolon () :
166+ if self .num_semis > 0 :
164167 if inst := self .streamer .readInstancePy (True ):
168+ self .num_semis -= 1
165169 return inst ["type" ], dict (list (inst .items ())[2 :])
166170 else :
167171 self .finalized = True
Original file line number Diff line number Diff line change @@ -139,7 +139,9 @@ class IFC_PARSE_API InstanceStreamer {
139139
140140 bool hasSemicolon () const ;
141141
142- void pushPage (const std::string& page);
142+ size_t semicolonCount () const ;
143+
144+ void pushPage (const std::string& page);
143145
144146 InstanceStreamer ();
145147
Original file line number Diff line number Diff line change @@ -1371,6 +1371,30 @@ bool IfcParse::InstanceStreamer::hasSemicolon() const {
13711371 return false ;
13721372}
13731373
1374+ size_t IfcParse::InstanceStreamer::semicolonCount () const {
1375+ auto local_stream = stream_->clone ();
1376+ auto local_lexer = IfcSpfLexer (&local_stream);
1377+ Token t;
1378+ size_t count = 0 ;
1379+ try {
1380+ t = local_lexer.Next ();
1381+ } catch (const std::out_of_range&) {
1382+ return false ;
1383+ }
1384+ while (t.type != Token_NONE) {
1385+ if (TokenFunc::isOperator (t, ' ;' )) {
1386+ count++;
1387+ }
1388+ try {
1389+ t = local_lexer.Next ();
1390+ } catch (const std::out_of_range&) {
1391+ // This most likely happens when a page boundary is contained within a string
1392+ break ;
1393+ }
1394+ }
1395+ return count;
1396+ }
1397+
13741398void IfcParse::InstanceStreamer::pushPage (const std::string& page)
13751399{
13761400 stream_->pushNextPage (page);
You can’t perform that action at this time.
0 commit comments