Skip to content

Commit 4a4ac22

Browse files
committed
Use subroutine to implement logicalloc
1 parent 7b5ffac commit 4a4ac22

File tree

2 files changed

+61
-7
lines changed

2 files changed

+61
-7
lines changed

src/stdlib_array.f90

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,7 @@ pure function trueloc(array, lbound) result(loc)
1818
!> Locations of true elements
1919
integer :: loc(count(array))
2020

21-
loc = logicalloc(array, .true., lbound)
21+
call logicalloc(loc, array, .true., lbound)
2222
end function trueloc
2323

2424
!> Return the positions of the false elements in array
@@ -30,19 +30,19 @@ pure function falseloc(array, lbound) result(loc)
3030
!> Locations of false elements
3131
integer :: loc(count(.not.array))
3232

33-
loc = logicalloc(array, .false., lbound)
33+
call logicalloc(loc, array, .false., lbound)
3434
end function falseloc
3535

3636
!> Return the positions of the truthy elements in array
37-
pure function logicalloc(array, truth, lbound) result(loc)
37+
pure subroutine logicalloc(loc, array, truth, lbound)
38+
!> Locations of truthy elements
39+
integer, intent(out) :: loc(:)
3840
!> Mask of logicals
3941
logical, intent(in) :: array(:)
4042
!> Truthy value
4143
logical, intent(in) :: truth
4244
!> Lower bound of array to index
4345
integer, intent(in), optional :: lbound
44-
!> Locations of truthy elements
45-
integer :: loc(count(array.eqv.truth))
4646
integer :: i, pos, offset
4747

4848
offset = 0
@@ -55,6 +55,6 @@ pure function logicalloc(array, truth, lbound) result(loc)
5555
loc(i) = pos + offset
5656
end if
5757
end do
58-
end function logicalloc
58+
end subroutine logicalloc
5959

6060
end module stdlib_array

src/tests/array/test_logicalloc.f90

Lines changed: 55 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,8 @@
22

33
module test_logicalloc
44
use stdlib_array, only : trueloc, falseloc
5-
use stdlib_string_type, only : string_type, len
5+
use stdlib_kinds, only : dp, i8 => int64
6+
use stdlib_strings, only : to_string
67
use testdrive, only : new_unittest, unittest_type, error_type, check
78
implicit none
89
private
@@ -75,23 +76,31 @@ subroutine test_trueloc_where(error)
7576

7677
integer :: ndim
7778
real, allocatable :: avec(:), bvec(:), cvec(:)
79+
real(dp) :: tl, tw
7880

81+
tl = 0.0_dp
82+
tw = 0.0_dp
7983
do ndim = 100, 12000, 100
8084
allocate(avec(ndim))
8185

8286
call random_number(avec)
8387
avec(:) = avec - 0.5
8488

8589
bvec = avec
90+
tl = tl - timing()
8691
bvec(trueloc(bvec > 0)) = 0.0
92+
tl = tl + timing()
8793

8894
cvec = avec
95+
tw = tw - timing()
8996
where(cvec > 0) cvec = 0.0
97+
tw = tw + timing()
9098

9199
call check(error, all(bvec == cvec))
92100
deallocate(avec, bvec, cvec)
93101
if (allocated(error)) exit
94102
end do
103+
call report("trueloc", tl, "where", tw)
95104
end subroutine test_trueloc_where
96105

97106
subroutine test_trueloc_merge(error)
@@ -100,23 +109,31 @@ subroutine test_trueloc_merge(error)
100109

101110
integer :: ndim
102111
real, allocatable :: avec(:), bvec(:), cvec(:)
112+
real(dp) :: tl, tm
103113

114+
tl = 0.0_dp
115+
tm = 0.0_dp
104116
do ndim = 100, 12000, 100
105117
allocate(avec(ndim))
106118

107119
call random_number(avec)
108120
avec(:) = avec - 0.5
109121

110122
bvec = avec
123+
tl = tl - timing()
111124
bvec(trueloc(bvec > 0)) = 0.0
125+
tl = tl + timing()
112126

113127
cvec = avec
128+
tm = tm - timing()
114129
cvec(:) = merge(0.0, cvec, cvec > 0)
130+
tm = tm + timing()
115131

116132
call check(error, all(bvec == cvec))
117133
deallocate(avec, bvec, cvec)
118134
if (allocated(error)) exit
119135
end do
136+
call report("trueloc", tl, "merge", tm)
120137
end subroutine test_trueloc_merge
121138

122139
subroutine test_falseloc_empty(error)
@@ -166,23 +183,31 @@ subroutine test_falseloc_where(error)
166183

167184
integer :: ndim
168185
real, allocatable :: avec(:), bvec(:), cvec(:)
186+
real(dp) :: tl, tw
169187

188+
tl = 0.0_dp
189+
tw = 0.0_dp
170190
do ndim = 100, 12000, 100
171191
allocate(avec(ndim))
172192

173193
call random_number(avec)
174194
avec(:) = avec - 0.5
175195

176196
bvec = avec
197+
tl = tl - timing()
177198
bvec(falseloc(bvec > 0)) = 0.0
199+
tl = tl + timing()
178200

179201
cvec = avec
202+
tw = tw - timing()
180203
where(.not.(cvec > 0)) cvec = 0.0
204+
tw = tw + timing()
181205

182206
call check(error, all(bvec == cvec))
183207
deallocate(avec, bvec, cvec)
184208
if (allocated(error)) exit
185209
end do
210+
call report("falseloc", tl, "where", tw)
186211
end subroutine test_falseloc_where
187212

188213
subroutine test_falseloc_merge(error)
@@ -191,25 +216,54 @@ subroutine test_falseloc_merge(error)
191216

192217
integer :: ndim
193218
real, allocatable :: avec(:), bvec(:), cvec(:)
219+
real(dp) :: tl, tm
194220

221+
tl = 0.0_dp
222+
tm = 0.0_dp
195223
do ndim = 100, 12000, 100
196224
allocate(avec(ndim))
197225

198226
call random_number(avec)
199227
avec(:) = avec - 0.5
200228

201229
bvec = avec
230+
tl = tl - timing()
202231
bvec(falseloc(bvec > 0)) = 0.0
232+
tl = tl + timing()
203233

204234
cvec = avec
235+
tm = tm - timing()
205236
cvec(:) = merge(cvec, 0.0, cvec > 0)
237+
tm = tm + timing()
206238

207239
call check(error, all(bvec == cvec))
208240
deallocate(avec, bvec, cvec)
209241
if (allocated(error)) exit
210242
end do
243+
call report("falseloc", tl, "merge", tm)
211244
end subroutine test_falseloc_merge
212245

246+
subroutine report(l1, t1, l2, t2)
247+
character(len=*), intent(in) :: l1, l2
248+
real(dp), intent(in) :: t1, t2
249+
character(len=*), parameter :: fmt = "f6.4"
250+
251+
!$omp critical
252+
print '(2x, "[Timing]", *(1x, g0))', &
253+
l1//":", to_string(t1, fmt)//"s", &
254+
l2//":", to_string(t2, fmt)//"s", &
255+
"ratio:", to_string(t1/t2, "f4.1")
256+
!$omp end critical
257+
end subroutine report
258+
259+
function timing() result(time)
260+
real(dp) :: time
261+
262+
integer(i8) :: time_count, time_rate, time_max
263+
call system_clock(time_count, time_rate, time_max)
264+
time = real(time_count, dp)/real(time_rate, dp)
265+
end function timing
266+
213267
end module test_logicalloc
214268

215269

0 commit comments

Comments
 (0)