Skip to content

Commit bbd85c7

Browse files
Copilotivan-pi
andauthored
Adjust solout initial callback and reorder solver stats
Agent-Logs-Url: https://github.com/ivan-pi/stiff3/sessions/8e92236a-2f09-487c-9169-cb3dc8700e1a Co-authored-by: ivan-pi <21085643+ivan-pi@users.noreply.github.com>
1 parent 85bdb2b commit bbd85c7

11 files changed

Lines changed: 35 additions & 47 deletions

README.md

Lines changed: 4 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,7 @@ This repository provides a heavily refactored version of the original implementa
1616
- Third-order Rosenbrock-type (semi-implicit Runge-Kutta) integrator suitable for stiff ODE systems
1717
- Adaptive stepsize control with error tolerance per component
1818
- Optional maximum absolute half-step size (`hmax`) to cap step growth
19-
- Optional runtime statistics output: rhs evaluations (`nfev`), Jacobian evaluations (`njev`), LU decompositions (`nlu`), successful steps (`nacc`), rejected steps (`nrej`), and linear-system solves (`nsol`)
19+
- Optional runtime statistics output: successful steps (`nacc`), rejected steps (`nrej`), rhs evaluations (`nfev`), Jacobian evaluations (`njev`), LU decompositions (`nlu`), and linear-system solves (`nsol`)
2020
- Optional explicit workspace interface via `stiff3(..., rwork, iwork, ...)` for caller-managed memory
2121
- Dense output helper `stiff3_interp` for accepted steps in `solout`
2222
- Requires an exact user-supplied Jacobian
@@ -95,7 +95,7 @@ program vanpol
9595
integer, parameter :: n = 2
9696
real(wp), parameter :: mu = 10.0_wp
9797
real(wp) :: y(n), w(n), x0, x1, h0, eps, hmax
98-
integer :: irtrn, stats(6)
98+
integer :: stats(6)
9999
100100
! initial value
101101
y = [1.0_wp, 1.0_wp]
@@ -109,13 +109,10 @@ program vanpol
109109
! time interval
110110
x0 = 0.0_wp
111111
x1 = 100.0_wp
112-
! output initial condition
113-
irtrn = 0
114-
call out(0,x0,x0,y,0,0.0_wp,irtrn)
115112
! integrate system of ODEs
116113
call stiff3(n,fun,x0,y,x1,jac,h0,eps,w,solout=out,stats=stats,hmax=hmax)
117-
print '(A,3(I0,1X))', 'nfev njev nlu: ', stats(1), stats(2), stats(3)
118-
print '(A,3(I0,1X))', 'accepted rejected nsol: ', stats(4), stats(5), stats(6)
114+
print '(A,3(I0,1X))', 'accepted rejected nfev: ', stats(1), stats(2), stats(3)
115+
print '(A,3(I0,1X))', 'njev nlu nsol: ', stats(4), stats(5), stats(6)
119116
120117
contains
121118

example/lorenz.f90

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,6 @@ program lorenz
77
integer, parameter :: n = 3
88
real(wp), parameter :: sigma = 10.0_wp, rho = 28.0_wp, beta = 8.0_wp/3.0_wp
99
real(wp) :: y(n), w(n), x0, x1, h0, eps
10-
integer :: irtrn
1110

1211
! initial value
1312
y = [1.0_wp, 1.0_wp, 1.0_wp]
@@ -19,9 +18,6 @@ program lorenz
1918
! time interval
2019
x0 = 0.0_wp
2120
x1 = 40.0_wp
22-
! output initial condition
23-
irtrn = 0
24-
call out(0,x0,x0,y,0,0.0_wp,irtrn)
2521
! integrate system of ODEs
2622
call stiff3(n,fun,x0,y,x1,jac,h0,eps,w,solout=out)
2723

example/pendant_drop.f90

Lines changed: 2 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -28,12 +28,10 @@ program pendant_drop
2828
eps = 1.0e-6_wp
2929
w = 1.0_wp
3030

31-
! output initial condition at s = 0
32-
write(*,'(4(E18.12,2X),I4,2X,G0)') 0.0_wp, 0.0_wp, 0.0_wp, 0.0_wp, 0, 0.0_wp
3331
! integrate Young-Laplace system
3432
call stiff3(n,fun,x0,y,x1,jac,h0,eps,w,solout=out,stats=stats)
35-
print '(A,3(I0,1X))', 'nfev njev nlu: ', stats(1), stats(2), stats(3)
36-
print '(A,3(I0,1X))', 'accepted rejected nsol: ', stats(4), stats(5), stats(6)
33+
print '(A,3(I0,1X))', 'accepted rejected nfev: ', stats(1), stats(2), stats(3)
34+
print '(A,3(I0,1X))', 'njev nlu nsol: ', stats(4), stats(5), stats(6)
3735

3836
contains
3937

example/predator_prey.f90

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,6 @@ program predator_prey
88
real(wp), parameter :: alpha = 1.1_wp, beta = 0.4_wp
99
real(wp), parameter :: delta = 0.1_wp, gamma = 0.4_wp
1010
real(wp) :: y(n), w(n), x0, x1, h0, eps
11-
integer :: irtrn
1211

1312
! initial value
1413
y = [10.0_wp, 5.0_wp]
@@ -20,9 +19,6 @@ program predator_prey
2019
! time interval
2120
x0 = 0.0_wp
2221
x1 = 40.0_wp
23-
! output initial condition
24-
irtrn = 0
25-
call out(0,x0,x0,y,0,0.0_wp,irtrn)
2622
! integrate system of ODEs
2723
call stiff3(n,fun,x0,y,x1,jac,h0,eps,w,solout=out)
2824

example/robertson.f90

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -49,7 +49,6 @@ program main
4949
real(wp) :: y(n), w(n)
5050
real(wp) :: h0, eps, x0, x1
5151

52-
integer :: irtrn
5352

5453
! initial value
5554
y = [1.0_wp, 0.0_wp, 0.0_wp]
@@ -66,8 +65,6 @@ program main
6665
x0 = 0.0_wp
6766
x1 = 10.0_wp
6867

69-
irtrn = 0
70-
call output(0,x0,x0,y,0,0.0_wp,irtrn)
7168
call stiff3(n,fun,x0,y,x1,dfun,h0,eps,w,solout=output)
7269

7370
contains

example/three_equation_system.f90

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -22,8 +22,8 @@ program three_equation_system
2222
x1 = 50.0_wp
2323

2424
call stiff3(n,fun,x0,y,x1,jac,h0,eps,w,stats=stats)
25-
print '(A,3(I0,1X))', 'nfev njev nlu: ', stats(1), stats(2), stats(3)
26-
print '(A,3(I0,1X))', 'accepted rejected nsol: ', stats(4), stats(5), stats(6)
25+
print '(A,3(I0,1X))', 'accepted rejected nfev: ', stats(1), stats(2), stats(3)
26+
print '(A,3(I0,1X))', 'njev nlu nsol: ', stats(4), stats(5), stats(6)
2727

2828
contains
2929

example/vanpol.f90

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,6 @@ program vanpol
66
integer, parameter :: n = 2
77
real(wp), parameter :: mu = 10.0_wp
88
real(wp) :: y(n), w(n), x0, x1, h0, eps
9-
integer :: irtrn
109

1110
! initial value
1211
y = [1.0_wp, 1.0_wp]
@@ -18,9 +17,6 @@ program vanpol
1817
! time interval
1918
x0 = 0.0_wp
2019
x1 = 100.0_wp
21-
! output initial condition
22-
irtrn = 0
23-
call out(0,x0,x0,y,0,0.0_wp,irtrn)
2420
! integrate system of ODEs
2521
call stiff3(n,fun,x0,y,x1,jac,h0,eps,w,solout=out)
2622

src/stiff3_solver.f90

Lines changed: 17 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -48,7 +48,7 @@ subroutine jacobian_sub(n,y,df)
4848
subroutine output_sub(nr,xold,x,y,iha,qa,irtrn)
4949
import wp
5050
integer, intent(in) :: nr
51-
!! Number of successful steps that have been taken
51+
!! Number of the current grid point, starting at 1 for the initial value
5252
real(wp), intent(in) :: xold
5353
!! Previous value of the independent variable
5454
real(wp), intent(in) :: x
@@ -106,7 +106,7 @@ subroutine stiff3_auto(n,fun,x,y,xend,jac,h0,eps,w,solout,stats,hmax)
106106
procedure(output_sub), optional :: solout
107107
!! User supplied subprogram for output.
108108
integer, intent(out), optional :: stats(6)
109-
!! Statistics array with `[nfev, njev, nlu, nacc, nrej, nsol]`.
109+
!! Statistics array with `[nacc, nrej, nfev, njev, nlu, nsol]`.
110110
real(wp), intent(in), optional :: hmax
111111
!! Maximum absolute half-step size. If absent or zero, defaults to
112112
!! `abs(xend - x)`.
@@ -154,7 +154,7 @@ subroutine stiff3_work(n,fun,x,y,xend,jac,h0,eps,w,rwork,iwork,solout,stats,hmax
154154
procedure(output_sub), optional :: solout
155155
!! User supplied subprogram for output.
156156
integer, intent(out), optional :: stats(6)
157-
!! Statistics array with `[nfev, njev, nlu, nacc, nrej, nsol]`.
157+
!! Statistics array with `[nacc, nrej, nfev, njev, nlu, nsol]`.
158158
real(wp), intent(in), optional :: hmax
159159
!! Maximum absolute half-step size. If absent or zero, defaults to
160160
!! `abs(xend - x)`.
@@ -194,15 +194,14 @@ subroutine stiff3_core(n,fun,x,y,xend,jac,h0,eps,w, &
194194
integer, intent(out), optional :: stats(6)
195195
real(wp), intent(in), optional :: hmax
196196

197-
integer :: icon, iha, i, j, nr, irtrn
197+
integer :: icon, iha, i, j, irtrn
198198
integer :: nfev, njev, nlu, nacc, nrej, nsol
199199
real(wp) :: x_current, xold, h, e, es, q, qa, hmax_used
200200
logical :: have_f
201201

202202
! icon = 0 except for last step which ends exactly at x1
203203
icon = 0
204204

205-
nr = 0
206205
x_current = x
207206
if (present(hmax)) then
208207
if (hmax < 0.0_wp) error stop 'stiff3: hmax must be a non-negative real value'
@@ -223,6 +222,16 @@ subroutine stiff3_core(n,fun,x,y,xend,jac,h0,eps,w, &
223222
nsol = 0
224223
have_f = .false.
225224

225+
if (present(solout)) then
226+
irtrn = 0
227+
call solout(1,x_current,x_current,y,0,0.0_wp,irtrn)
228+
if (irtrn < 0) then
229+
h0 = h
230+
if (present(stats)) stats = [nacc, nrej, nfev, njev, nlu, nsol]
231+
return
232+
end if
233+
end if
234+
226235
outer: do
227236

228237
! last step - or first step longer than interval
@@ -342,14 +351,13 @@ subroutine stiff3_core(n,fun,x,y,xend,jac,h0,eps,w, &
342351

343352
! perform output if appropriate
344353

345-
nr = nr + 1
346354
nacc = nacc + 1
347355
if (present(solout)) then
348356
irtrn = 0
349-
call solout(nr,xold,x_current,y,iha,qa,irtrn)
357+
call solout(nacc+1,xold,x_current,y,iha,qa,irtrn)
350358
if (irtrn < 0) then
351359
h0 = h
352-
if (present(stats)) stats = [nfev, njev, nlu, nacc, nrej, nsol]
360+
if (present(stats)) stats = [nacc, nrej, nfev, njev, nlu, nsol]
353361
return
354362
end if
355363
end if
@@ -358,7 +366,7 @@ subroutine stiff3_core(n,fun,x,y,xend,jac,h0,eps,w, &
358366

359367
if (icon == 1) then
360368
h0 = h
361-
if (present(stats)) stats = [nfev, njev, nlu, nacc, nrej, nsol]
369+
if (present(stats)) stats = [nacc, nrej, nfev, njev, nlu, nsol]
362370
return
363371
end if
364372

test/ode_hmax.f90

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -27,7 +27,7 @@ program ode_hmax
2727

2828
if (any(stats_zero /= stats_default)) then
2929
print '(A,6(I0,1X),A,6(I0,1X))', &
30-
'expected hmax=0 stats [nfev njev nlu nacc nrej nsol] to match default. got ', stats_zero, &
30+
'expected hmax=0 stats [nacc nrej nfev njev nlu nsol] to match default. got ', stats_zero, &
3131
' expected ', stats_default
3232
error stop 1
3333
end if

test/ode_stats.f90

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -50,25 +50,25 @@ program ode_stats
5050

5151
call stiff3(n,fun,x0,y,x1,jac,h0,eps,w,stats=stats)
5252

53-
if (stats(1) /= fun_calls .or. stats(2) /= jac_calls) then
53+
if (stats(3) /= fun_calls .or. stats(4) /= jac_calls) then
5454
print '(A,6(I0,1X),A,2(I0,1X))', &
55-
'stats mismatch [nfev njev nlu nacc nrej nsol]: ', stats, &
55+
'stats mismatch [nacc nrej nfev njev nlu nsol]: ', stats, &
5656
' callback counts [fun jac]: ', fun_calls, jac_calls
5757
error stop 1
5858
end if
5959

60-
if (stats(3) <= 0) then
61-
print '(A,6(I0,1X))', 'expected positive nlu in stats [nfev njev nlu nacc nrej nsol], got: ', stats
60+
if (stats(5) <= 0) then
61+
print '(A,6(I0,1X))', 'expected positive nlu in stats [nacc nrej nfev njev nlu nsol], got: ', stats
6262
error stop 1
6363
end if
6464

65-
if (stats(4) <= 0 .or. stats(5) < 0) then
66-
print '(A,6(I0,1X))', 'expected nonnegative step counters [nfev njev nlu nacc nrej nsol], got: ', stats
65+
if (stats(1) <= 0 .or. stats(2) < 0) then
66+
print '(A,6(I0,1X))', 'expected nonnegative step counters [nacc nrej nfev njev nlu nsol], got: ', stats
6767
error stop 1
6868
end if
6969

70-
if (stats(6) < stats(3)) then
71-
print '(A,6(I0,1X))', 'expected nsol>=nlu in stats [nfev njev nlu nacc nrej nsol], got: ', stats
70+
if (stats(6) < stats(5)) then
71+
print '(A,6(I0,1X))', 'expected nsol>=nlu in stats [nacc nrej nfev njev nlu nsol], got: ', stats
7272
error stop 1
7373
end if
7474

0 commit comments

Comments
 (0)