46
46
* ` ORD_SORT ` is intended to sort simple arrays of intrinsic data
47
47
that have significant sections that were partially ordered before
48
48
the sort;
49
+ * ` SORT_ADJ ` is based on ` ORD_SORT ` , but in addition to sorting the
50
+ input array, it returns a related array re-ordered in the
51
+ same way;
49
52
* ` SORT_INDEX ` is based on ` ORD_SORT ` , but in addition to sorting the
50
53
input array, it returns indices that map the original array to its
51
54
sorted version. This enables related arrays to be re-ordered in the
@@ -60,10 +63,10 @@ data:
60
63
The Fortran Standard Library is distributed under the MIT
61
64
License. However components of the library may be based on code with
62
65
additional licensing restrictions. In particular ` ORD_SORT ` ,
63
- ` SORT_INDEX ` , and ` SORT ` are translations of codes with their
66
+ ` SORT_ADJ ` , ` SORT_INDEX ` , and ` SORT ` are translations of codes with their
64
67
own distribution restrictions.
65
68
66
- The ` ORD_SORT ` and ` SORT_INDEX ` subroutines are essentially
69
+ The ` ORD_SORT ` , ` SORT_ADJ ` and ` SORT_INDEX ` subroutines are essentially
67
70
translations to Fortran 2008 of the ` "Rust" sort ` of the Rust Language
68
71
distributed as part of
69
72
[ ` slice.rs ` ] ( https://github.com/rust-lang/rust/blob/90eb44a5897c39e3dff9c7e48e3973671dcd9496/src/liballoc/slice.rs ) .
@@ -140,6 +143,24 @@ argument or allocated internally on the stack.
140
143
Arrays can be also sorted in a decreasing order by providing the argument `reverse
141
144
= .true.`.
142
145
146
+ #### The ` SORT_ADJ ` subroutine
147
+
148
+ The ` SORT ` and ` ORD_SORT ` subroutines can sort rank 1 isolated
149
+ arrays of intrinsic types, but do nothing for the coordinated sorting
150
+ of related data, e.g., a related rank 1 array. Therefore the module
151
+ provides a subroutine, ` SORT_ADJ ` , that re-order such a rank 1 array
152
+ in the same way as the input array based on the ` ORD_SORT ` algorithm,
153
+ in addition to sorting the input array.
154
+
155
+ The logic of ` SORT_ADJ ` parallels that of ` ORD_SORT ` , with
156
+ additional housekeeping to keep the associated array consistent with
157
+ the sorted positions of the input array. Because of this additional
158
+ housekeeping it has slower runtime performance than ` ORD_SORT ` .
159
+ ` SORT_ADJ ` requires the use of two "scratch" arrays, that may be
160
+ provided as optional ` work ` and ` iwork ` arguments or allocated
161
+ internally on the stack.
162
+
163
+
143
164
#### The ` SORT_INDEX ` subroutine
144
165
145
166
The ` SORT ` and ` ORD_SORT ` subroutines can sort rank 1 isolated
@@ -198,7 +219,7 @@ factor of six. Still, even when it shows enhanced performance, its
198
219
performance on partially sorted data is typically an order of
199
220
magnitude slower than ` ORD_SORT ` . Its memory requirements are also
200
221
low, being of order O(Ln(N)), while the memory requirements of
201
- ` ORD_SORT ` and ` SORT_INDEX ` are of order O(N).
222
+ ` ORD_SORT ` , ` SORT_ADJ ` and ` SORT_INDEX ` are of order O(N).
202
223
203
224
#### The ` RADIX_SORT ` subroutine
204
225
@@ -385,6 +406,84 @@ element of `array` is a `NaN`.
385
406
{!example/sorting/example_radix_sort.f90!}
386
407
```
387
408
409
+ #### ` sort_adj ` - sorts an associated array in the same way as the input array, while also sorting the array.
410
+
411
+ ##### Status
412
+
413
+ Experimental
414
+
415
+ ##### Description
416
+
417
+ Returns the input ` array ` sorted in the direction requested while
418
+ retaining order stability, and an associated array whose elements are
419
+ sorted in the same way as the input ` array ` .
420
+
421
+ ##### Syntax
422
+
423
+ ` call ` [[ stdlib_sorting(module): sort_adj (interface)]] ` ( array, index[, work, iwork, reverse ] ) `
424
+
425
+ ##### Class
426
+
427
+ Generic subroutine.
428
+
429
+ ##### Arguments
430
+
431
+ ` array ` : shall be a rank one array of any of the types:
432
+ ` integer(int8) ` , ` integer(int16) ` , ` integer(int32) ` , ` integer(int64) ` ,
433
+ ` real(sp) ` , ` real(dp) ` , ` real(qp) ` , ` character(*) ` , ` type(string_type) ` ,
434
+ ` type(bitset_64) ` , or ` type(bitset_large) ` .
435
+ It is an ` intent(inout) ` argument. On input it
436
+ will be an array whose sorting indices are to be determined. On return
437
+ it will be the sorted array.
438
+
439
+ ` index ` : shall be a rank one ` integer ` or ` real ` array of
440
+ the size of ` array ` . It is an ` intent(inout) ` argument. On return it
441
+ shall have values that are the indices needed to sort the original
442
+ array in the desired direction.
443
+
444
+ ` work ` (optional): shall be a rank one array of any of the same type as
445
+ ` array ` , and shall have at least ` size(array)/2 ` elements. It is an
446
+ ` intent(out) ` argument. It is intended to be used as "scratch"
447
+ memory for internal record keeping. If associated with an array in
448
+ static storage, its use can significantly reduce the stack memory
449
+ requirements for the code. Its contents on return are undefined.
450
+
451
+ ` iwork ` (optional): shall be a rank one integer array of the same kind
452
+ of the array ` index ` , and shall have at least ` size(array)/2 ` elements. It
453
+ is an ` intent(out) ` argument. It is intended to be used as "scratch"
454
+ memory for internal record keeping. If associated with an array in
455
+ static storage, its use can significantly reduce the stack memory
456
+ requirements for the code. Its contents on return are undefined.
457
+
458
+ ` reverse ` (optional): shall be a scalar of type default logical. It
459
+ is an ` intent(in) ` argument. If present with a value of ` .true. ` then
460
+ ` array ` will be sorted in order of non-increasing values in stable
461
+ order. Otherwise ` array ` will be sorted in order of non-decreasing
462
+ values in stable order.
463
+
464
+ ##### Notes
465
+
466
+ ` SORT_ADJ ` implements the hybrid sorting algorithm of ` ORD_SORT ` ,
467
+ keeping the values of ` index ` consistent with the elements of ` array `
468
+ as it is sorted. As a ` merge sort ` based algorithm, it is a stable
469
+ sorting comparison algorithm. The optional ` work ` and ` iwork ` arrays
470
+ replace "scratch" memory that would otherwise be allocated on the
471
+ stack. If ` array ` is of any kind of ` REAL ` the order of the elements in
472
+ ` index ` and ` array ` on return are undefined if any element of ` array `
473
+ is a ` NaN ` . Sorting of ` CHARACTER(*) ` and ` STRING_TYPE ` arrays are
474
+ based on the operator ` > ` , and not on the function ` LGT ` .
475
+
476
+ It should be emphasized that the order of ` array ` will typically be
477
+ different on return
478
+
479
+ ##### Examples
480
+
481
+ Sorting a rank one array with ` sort_adj ` :
482
+
483
+ ``` Fortran
484
+ {!example/sorting/example_sort_adj.f90!}
485
+ ```
486
+
388
487
#### ` sort_index ` - creates an array of sorting indices for an input array, while also sorting the array.
389
488
390
489
##### Status
0 commit comments