@@ -175,62 +175,60 @@ export const executeFormula = function (expression, x, y) {
175175
176176 // Get tokens
177177 tokens = expression . match ( / ( [ A - Z ] + [ 0 - 9 ] + ) / g) ;
178+ tokens = new Set ( tokens ) ;
178179
179180 // Direct self-reference protection
180- if ( tokens && tokens . indexOf ( parentId ) > - 1 ) {
181+ if ( tokens && tokens . has ( parentId ) ) {
181182 console . error ( 'Self Reference detected' ) ;
182183 return '#ERROR' ;
183184 } else {
184185 // Expressions to be used in the parsing
185186 const formulaExpressions = { } ;
186187
187188 if ( tokens ) {
188- for ( let i = 0 ; i < tokens . length ; i ++ ) {
189+ for ( const t of tokens ) {
189190 // Keep chain
190- if ( ! obj . formula [ tokens [ i ] ] ) {
191- obj . formula [ tokens [ i ] ] = [ ] ;
191+ if ( ! obj . formula [ t ] ) {
192+ obj . formula [ t ] = new Set ( ) ;
192193 }
193194 // Is already in the register
194- if ( obj . formula [ tokens [ i ] ] . indexOf ( parentId ) < 0 ) {
195- obj . formula [ tokens [ i ] ] . push ( parentId ) ;
196- }
195+ obj . formula [ t ] . add ( parentId ) ;
197196
198197 // Do not calculate again
199- if ( eval ( 'typeof(' + tokens [ i ] + ') == "undefined"' ) ) {
198+ if ( ! ( t in globalThis ) ) {
200199 // Coords
201- const position = getIdFromColumnName ( tokens [ i ] , 1 ) ;
200+ const position = getIdFromColumnName ( t , 1 ) ;
202201 // Get value
203202 let value ;
204203
205- if ( typeof obj . options . data [ position [ 1 ] ] != 'undefined' && typeof obj . options . data [ position [ 1 ] ] [ position [ 0 ] ] != 'undefined' ) {
204+ if ( position [ 1 ] in obj . options . data && position [ 0 ] in obj . options . data [ position [ 1 ] ] ) {
206205 value = obj . options . data [ position [ 1 ] ] [ position [ 0 ] ] ;
207206 } else {
208207 value = '' ;
209208 }
210209 // Get column data
211210 if ( ( '' + value ) . substr ( 0 , 1 ) == '=' ) {
212- if ( typeof formulaResults [ tokens [ i ] ] !== 'undefined' ) {
213- value = formulaResults [ tokens [ i ] ] ;
211+ if ( t in formulaResults ) {
212+ value = formulaResults [ t ] ;
214213 } else {
215214 value = execute ( value , position [ 0 ] , position [ 1 ] ) ;
216- formulaResults [ tokens [ i ] ] = value ;
215+ formulaResults [ t ] = value ;
217216 }
218217 }
219218 // Type!
220219 if ( ( '' + value ) . trim ( ) == '' ) {
221- // Null
222- formulaExpressions [ tokens [ i ] ] = null ;
220+ delete formulaExpressions [ t ] ;
223221 } else {
224222 if ( value == Number ( value ) && obj . parent . config . autoCasting != false ) {
225223 // Number
226- formulaExpressions [ tokens [ i ] ] = Number ( value ) ;
224+ formulaExpressions [ t ] = Number ( value ) ;
227225 } else {
228226 // Trying any formatted number
229227 const number = parseNumber . call ( obj , value , position [ 0 ] ) ;
230228 if ( obj . parent . config . autoCasting != false && number ) {
231- formulaExpressions [ tokens [ i ] ] = number ;
229+ formulaExpressions [ t ] = number ;
232230 } else {
233- formulaExpressions [ tokens [ i ] ] = '"' + value + '"' ;
231+ formulaExpressions [ t ] = '"' + value + '"' ;
234232 }
235233 }
236234 }
@@ -773,23 +771,23 @@ export const updateFormulaChain = function (x, y, records) {
773771 const obj = this ;
774772
775773 const cellId = getColumnNameFromId ( [ x , y ] ) ;
776- if ( obj . formula [ cellId ] && obj . formula [ cellId ] . length > 0 ) {
774+ if ( obj . formula [ cellId ] && obj . formula [ cellId ] . size > 0 ) {
777775 if ( chainLoopProtection [ cellId ] ) {
778776 obj . records [ y ] [ x ] . element . innerHTML = '#ERROR' ;
779777 obj . formula [ cellId ] = '' ;
780778 } else {
781779 // Protection
782780 chainLoopProtection [ cellId ] = true ;
783781
784- for ( let i = 0 ; i < obj . formula [ cellId ] . length ; i ++ ) {
785- const cell = getIdFromColumnName ( obj . formula [ cellId ] [ i ] , true ) ;
782+ for ( const n of obj . formula [ cellId ] ) {
783+ const cell = getIdFromColumnName ( n , true ) ;
786784 // Update cell
787785 const value = '' + obj . options . data [ cell [ 1 ] ] [ cell [ 0 ] ] ;
788786 if ( value . substr ( 0 , 1 ) == '=' ) {
789787 records . push ( updateCell . call ( obj , cell [ 0 ] , cell [ 1 ] , value , true ) ) ;
790788 } else {
791789 // No longer a formula, remove from the chain
792- Object . keys ( obj . formula ) [ i ] = null ;
790+ obj . formula [ cellId ] . delete ( n ) ;
793791 }
794792 updateFormulaChain . call ( obj , cell [ 0 ] , cell [ 1 ] , records ) ;
795793 }
@@ -874,13 +872,12 @@ const updateFormulas = function (referencesToUpdate) {
874872 key = referencesToUpdate [ key ] ;
875873 }
876874 // Update values
877- formula [ key ] = [ ] ;
878- for ( let i = 0 ; i < value . length ; i ++ ) {
879- let letter = value [ i ] ;
875+ formula [ key ] = new Set ( ) ;
876+ for ( let letter of value ) {
880877 if ( referencesToUpdate [ letter ] ) {
881878 letter = referencesToUpdate [ letter ] ;
882879 }
883- formula [ key ] . push ( letter ) ;
880+ formula [ key ] . add ( letter ) ;
884881 }
885882 }
886883 obj . formula = formula ;
0 commit comments