@@ -35,6 +35,7 @@ module function_parser
3535 ! parameters:
3636 real (wp), parameter :: zero = 0.0_wp
3737 real (wp), parameter :: one = 1.0_wp
38+ real (wp), parameter :: pi = acos (- one)
3839
3940 ! Note: these should be continuous, unique integers:
4041 ! [they must have the values that correspond to the array indices below]
@@ -60,8 +61,8 @@ module function_parser
6061 cAcos = 20 , &
6162 cAtan2 = 21 , & ! atan2 must precede atan to prevent aliasing.
6263 cAtan = 22 , &
63- cTest0 = 23 , & ! Test function with 0 arguments (returns 15.0).
64- cTest3 = 24 ! Test function with 3 arguments (returns sum of arguments).
64+ cPi = 23 , & ! Pi ( function with zero arguments)
65+ cIf = 24 ! Test function with 3 arguments (returns sum of arguments).
6566 integer , parameter :: VarBegin = 25
6667
6768 character (len= 1 ), dimension (cAdd:cPow), parameter :: operators = [ ' +' , & ! plus
@@ -70,7 +71,7 @@ module function_parser
7071 ' /' , & ! divide
7172 ' ^' ] ! power
7273
73- character (len= 5 ), dimension (cAbs:cTest3 ), parameter :: functions = [ ' abs ' , &
74+ character (len= 5 ), dimension (cAbs:cIf ), parameter :: functions = [ ' abs ' , &
7475 ' exp ' , &
7576 ' log10' , &
7677 ' log ' , &
@@ -85,11 +86,11 @@ module function_parser
8586 ' acos ' , &
8687 ' atan2' , &
8788 ' atan ' , &
88- ' test0 ' , &
89- ' test3 ' ]
89+ ' pi ' , &
90+ ' if ' ]
9091
9192 ! Specify the number of required arguments each `functions` element must have.
92- integer , dimension (cAbs:cTest3 ), parameter :: required_args = [ 1 , & ! abs
93+ integer , dimension (cAbs:cIf ), parameter :: required_args = [ 1 , & ! abs
9394 1 , & ! exp
9495 1 , & ! log10
9596 1 , & ! log
@@ -104,11 +105,11 @@ module function_parser
104105 1 , & ! acos
105106 2 , & ! atan2
106107 1 , & ! atan
107- 0 , & ! test0
108- 3 ] ! test3
108+ 0 , & ! pi
109+ 3 ] ! if
109110
110111 ! Specify the number of optional arguments each `functions` element might have.
111- integer , dimension (cAbs:cTest3 ), parameter :: optional_args = [ 0 , & ! abs
112+ integer , dimension (cAbs:cIf ), parameter :: optional_args = [ 0 , & ! abs
112113 0 , & ! exp
113114 0 , & ! log10
114115 0 , & ! log
@@ -123,8 +124,8 @@ module function_parser
123124 0 , & ! acos
124125 0 , & ! atan2
125126 1 , & ! atan
126- 0 , & ! test0
127- 0 ] ! test3
127+ 0 , & ! pi
128+ 0 ] ! if
128129
129130 ! The maximum number of arguments any `functions` element might have.
130131 integer , parameter :: max_func_args = maxval (required_args + optional_args)
@@ -1042,9 +1043,9 @@ end subroutine catan2_func
10421043
10431044! ******************************************************************
10441045! >
1045- ! Test function with zero arguments.
1046+ ! Pi. A function with zero arguments.
10461047
1047- subroutine ctest0_func (me ,ip ,dp ,sp ,val ,ierr )
1048+ subroutine cPi_func (me ,ip ,dp ,sp ,val ,ierr )
10481049
10491050 implicit none
10501051
@@ -1056,17 +1057,21 @@ subroutine ctest0_func(me,ip,dp,sp,val,ierr)
10561057 integer ,intent (out ) :: ierr ! ! error flag
10571058
10581059 sp = sp + 1
1059- me% stack(sp) = 15.0_wp
1060+ me% stack(sp) = pi
10601061 ierr = 0
10611062
1062- end subroutine ctest0_func
1063+ end subroutine cPi_func
10631064! ******************************************************************
10641065
10651066! ******************************************************************
10661067! >
1067- ! Test function with three arguments.
1068+ ! If function with three arguments.
1069+ !
1070+ ! `If(expression, value is true, value if false)`
1071+ !
1072+ ! Where: 0 is false and /=0 is true.
10681073
1069- subroutine ctest3_func (me ,ip ,dp ,sp ,val ,ierr )
1074+ subroutine cif_func (me ,ip ,dp ,sp ,val ,ierr )
10701075
10711076 implicit none
10721077
@@ -1077,11 +1082,16 @@ subroutine ctest3_func(me,ip,dp,sp,val,ierr)
10771082 real (wp),dimension (:),intent (in ) :: val ! ! variable values
10781083 integer ,intent (out ) :: ierr ! ! error flag
10791084
1080- me% stack(sp-2 ) = me% stack(sp-2 ) + me% stack(sp-1 ) + me% stack(sp)
1085+ if (me% stack(sp-2 ) /= zero) then ! true
1086+ me% stack(sp-2 ) = me% stack(sp-1 )
1087+ else ! false
1088+ me% stack(sp-2 ) = me% stack(sp)
1089+ end if
1090+
10811091 sp = sp - 2
10821092 ierr = 0
10831093
1084- end subroutine ctest3_func
1094+ end subroutine cif_func
10851095! ******************************************************************
10861096
10871097! ******************************************************************
@@ -1136,9 +1146,9 @@ subroutine find_arg_positions(paren_start, func, num_args, arg_pos, ierr, err_po
11361146 integer :: cur_pos, & ! ! The current position in `func` being processed.
11371147 func_len, & ! ! The length of `func`.
11381148 open_parens, & ! ! The number of open parentheses.
1139- arg_len, & ! ! The length of an argument.
1149+ arg_len, & ! ! The length of an argument.
11401150 iarg ! ! Argument index.
1141-
1151+
11421152 ! Initialize outputs.
11431153 num_args = 1
11441154 arg_pos = 0
@@ -1147,14 +1157,14 @@ subroutine find_arg_positions(paren_start, func, num_args, arg_pos, ierr, err_po
11471157
11481158 func_len = len_trim (func)
11491159 open_parens = 1
1150-
1160+
11511161 cur_pos = paren_start + 1
11521162 func_len = len_trim (func)
11531163
11541164 ! Step through the function string until we find the function's closing parenthesis.
11551165 ! Every time we find a comma character at the same parentheses level as the function's
1156- ! opening parenthesis, increment the number of arguments and record the previous
1157- ! argument's last character.
1166+ ! opening parenthesis, increment the number of arguments and record the previous
1167+ ! argument's last character.
11581168 do while (open_parens > 0 )
11591169 if (cur_pos > func_len) then
11601170 ! The function did not have a closing parenthesis.
@@ -1176,7 +1186,7 @@ subroutine find_arg_positions(paren_start, func, num_args, arg_pos, ierr, err_po
11761186 end if
11771187
11781188 open_parens = open_parens - 1
1179-
1189+
11801190 ! We have arrived at the function's closing parenthesis.
11811191 if (open_parens == 0 ) arg_pos(num_args) = cur_pos - 1
11821192
@@ -1203,9 +1213,9 @@ subroutine find_arg_positions(paren_start, func, num_args, arg_pos, ierr, err_po
12031213 do iarg = 1 , num_args
12041214 if (iarg == 1 ) then
12051215 arg_len = arg_pos(iarg) - paren_start
1206- else
1216+ else
12071217 arg_len = arg_pos(iarg) - arg_pos(iarg - 1 ) - 1
1208- endif
1218+ endif
12091219
12101220 if (arg_len == 0 ) then
12111221 if (present (ierr)) ierr = empty_arg
@@ -1215,7 +1225,7 @@ subroutine find_arg_positions(paren_start, func, num_args, arg_pos, ierr, err_po
12151225 end do
12161226
12171227 end subroutine find_arg_positions
1218-
1228+ ! *******************************************************************************
12191229
12201230! *******************************************************************************
12211231! >
@@ -1254,7 +1264,7 @@ recursive subroutine check_syntax (me,func,funcstr,var,ipos)
12541264 if (c == ' (' ) then
12551265 parcnt = parcnt + 1
12561266 elseif (c == ' )' ) then
1257- parcnt = parcnt - 1
1267+ parcnt = parcnt - 1
12581268 end if
12591269
12601270 if (parcnt < 0 ) then
@@ -1306,25 +1316,25 @@ recursive subroutine check_syntax (me,func,funcstr,var,ipos)
13061316 call me% add_error(j, ipos, funcstr, ' Missing opening parenthesis' )
13071317 return
13081318 end if
1309-
1319+
13101320 ! Find the number of function arguments and argument substring positions
13111321 ! in `func`.
13121322 call find_arg_positions(j, func, num_args, arg_pos, ierr, err_pos)
13131323 if (ierr /= 0 ) then
13141324 select case (ierr)
1315- case (1 ); call me% add_error(err_pos, ipos, funcstr, ' Missing function closing parenthesis' )
1325+ case (1 ); call me% add_error(err_pos, ipos, funcstr, ' Missing function closing parenthesis' )
13161326 case (2 ); call me% add_error(err_pos, ipos, funcstr, ' Function has too many arguments' )
13171327 case (3 ); call me% add_error(err_pos, ipos, funcstr, ' Function has an empty argument' )
13181328 case default ; call me% add_error(err_pos, ipos, funcstr, ' Unknown find argument position error' )
13191329 end select
13201330 return
13211331 end if
13221332
1323- ! Verify that the number of function arguments present is consistent
1333+ ! Verify that the number of function arguments present is consistent
13241334 ! with the specified function.
13251335 if (num_args < required_args(n)) then
13261336 call me% add_error(j, ipos, funcstr, ' Missing required function argument' )
1327- return
1337+ return
13281338 elseif (num_args > required_args(n) + optional_args(n)) then
13291339 call me% add_error(j, ipos, funcstr, ' Too many function arguments' )
13301340 return
@@ -1336,7 +1346,7 @@ recursive subroutine check_syntax (me,func,funcstr,var,ipos)
13361346 else
13371347 do iarg = 1 , num_args
13381348 if (iarg == 1 ) then
1339- arg_start = j + 1
1349+ arg_start = j + 1
13401350 else
13411351 arg_start = arg_pos(iarg-1 ) + 2
13421352 endif
@@ -1346,7 +1356,7 @@ recursive subroutine check_syntax (me,func,funcstr,var,ipos)
13461356
13471357 call me% check_syntax(func(arg_start:arg_end), funcstr, var, func_arg_ipos)
13481358 if (me% error()) return
1349- end do
1359+ end do
13501360
13511361 j = arg_pos(num_args) + 2
13521362 endif
@@ -1518,7 +1528,7 @@ function mathfunction_index (str) result (n)
15181528 character (len= len (functions)) :: fun
15191529
15201530 n = 0
1521- do j= cAbs,cTest3 ! check all math functions
1531+ do j= cAbs,cIf ! check all math functions
15221532 k = min (len_trim (functions(j)), len (str))
15231533 call to_lowercase (str(1 :k), fun)
15241534 if (fun == functions(j)) then ! compare lower case letters
@@ -1724,8 +1734,8 @@ subroutine add_compiled_byte (me, b, num_args)
17241734 case (1 ); me% bytecode_ops(me% bytecodesize)% f = > catan_func
17251735 case (2 ); me% bytecode_ops(me% bytecodesize)% f = > catan2_func
17261736 end select
1727- case (cTest0 ); me% bytecode_ops(me% bytecodesize)% f = > ctest0_func
1728- case (cTest3 ); me% bytecode_ops(me% bytecodesize)% f = > ctest3_func
1737+ case (cPi ); me% bytecode_ops(me% bytecodesize)% f = > cPi_func
1738+ case (cIf ); me% bytecode_ops(me% bytecodesize)% f = > cif_func
17291739 case default ; me% bytecode_ops(me% bytecodesize)% f = > cdefault_func
17301740 end select
17311741
@@ -1749,7 +1759,7 @@ function mathitem_index (me, f, var) result (n)
17491759 integer :: n ! ! byte value of math item
17501760
17511761 n = 0
1752- if (len (f)==0 ) return ! error condition
1762+ if (len (f)==0 ) return ! error condition
17531763
17541764 if (scan (f(1 :1 ),' 0123456789.' ) > 0 ) then ! check for begin of a number
17551765 me% immedsize = me% immedsize + 1
@@ -1845,7 +1855,7 @@ recursive subroutine compile_substr (me, f, b, e, var)
18451855 end do
18461856 else
18471857 me% stackptr = me% stackptr + 1
1848- if (me% stackptr > me% stacksize) me% stacksize = me% stacksize + 1
1858+ if (me% stackptr > me% stacksize) me% stacksize = me% stacksize + 1
18491859 end if
18501860
18511861 call add_compiled_byte (me, n, num_args)
@@ -1877,7 +1887,7 @@ recursive subroutine compile_substr (me, f, b, e, var)
18771887 end do
18781888 else
18791889 me% stackptr = me% stackptr + 1
1880- if (me% stackptr > me% stacksize) me% stacksize = me% stacksize + 1
1890+ if (me% stackptr > me% stacksize) me% stacksize = me% stacksize + 1
18811891 end if
18821892
18831893 call add_compiled_byte (me, n, num_args)
0 commit comments