program string_functions
use iso_fortran_env, only: stdout => output_unit
implicit none
! Declare variables
character(len=:), allocatable :: str1, str2, result
logical :: contains, has_prefix, has_suffix
integer :: count, index_pos
character(len=:), allocatable :: joined, repeated, replaced
character(len=10), dimension(5) :: split_result
! Define a subroutine for printing
interface
subroutine print_result(label, value)
character(len=*), intent(in) :: label
class(*), intent(in) :: value
end subroutine print_result
end interface
! String operations
str1 = "test"
str2 = "es"
! Contains
contains = index(str1, str2) > 0
call print_result("Contains: ", contains)
! Count
count = count_substring(str1, "t")
call print_result("Count: ", count)
! HasPrefix
has_prefix = str1(1:2) == "te"
call print_result("HasPrefix: ", has_prefix)
! HasSuffix
has_suffix = str1(len(str1)-1:) == "st"
call print_result("HasSuffix: ", has_suffix)
! Index
index_pos = index(str1, "e")
call print_result("Index: ", index_pos)
! Join
joined = join(["a", "b"], "-")
call print_result("Join: ", joined)
! Repeat
repeated = repeat("a", 5)
call print_result("Repeat: ", repeated)
! Replace
replaced = replace_all("foo", "o", "0")
call print_result("Replace: ", replaced)
replaced = replace_first("foo", "o", "0")
call print_result("Replace: ", replaced)
! Split
call split("a-b-c-d-e", "-", split_result)
call print_result("Split: ", split_result)
! ToLower
result = to_lower("TEST")
call print_result("ToLower: ", result)
! ToUpper
result = to_upper("test")
call print_result("ToUpper: ", result)
contains
function count_substring(str, substr) result(count)
character(len=*), intent(in) :: str, substr
integer :: count, i
count = 0
i = 1
do while (i <= len(str) - len(substr) + 1)
if (str(i:i+len(substr)-1) == substr) then
count = count + 1
i = i + len(substr)
else
i = i + 1
end if
end do
end function count_substring
function join(arr, sep) result(joined)
character(len=*), dimension(:), intent(in) :: arr
character(len=*), intent(in) :: sep
character(len=:), allocatable :: joined
integer :: i
joined = arr(1)
do i = 2, size(arr)
joined = joined // sep // arr(i)
end do
end function join
function replace_all(str, old, new) result(replaced)
character(len=*), intent(in) :: str, old, new
character(len=:), allocatable :: replaced
integer :: i
replaced = str
do i = 1, len(str) - len(old) + 1
if (replaced(i:i+len(old)-1) == old) then
replaced = replaced(:i-1) // new // replaced(i+len(old):)
end if
end do
end function replace_all
function replace_first(str, old, new) result(replaced)
character(len=*), intent(in) :: str, old, new
character(len=:), allocatable :: replaced
integer :: i
replaced = str
do i = 1, len(str) - len(old) + 1
if (replaced(i:i+len(old)-1) == old) then
replaced = replaced(:i-1) // new // replaced(i+len(old):)
exit
end if
end do
end function replace_first
subroutine split(str, sep, result)
character(len=*), intent(in) :: str, sep
character(len=*), dimension(:), intent(out) :: result
integer :: i, j, k
i = 1
k = 1
do j = 1, len(str)
if (str(j:j) == sep .or. j == len(str)) then
if (j == len(str)) j = j + 1
result(k) = str(i:j-1)
i = j + 1
k = k + 1
end if
end do
end subroutine split
function to_lower(str) result(lower)
character(len=*), intent(in) :: str
character(len=:), allocatable :: lower
integer :: i, j
lower = str
do i = 1, len(str)
j = iachar(str(i:i))
if (j >= iachar('A') .and. j <= iachar('Z')) then
lower(i:i) = achar(j + 32)
end if
end do
end function to_lower
function to_upper(str) result(upper)
character(len=*), intent(in) :: str
character(len=:), allocatable :: upper
integer :: i, j
upper = str
do i = 1, len(str)
j = iachar(str(i:i))
if (j >= iachar('a') .and. j <= iachar('z')) then
upper(i:i) = achar(j - 32)
end if
end do
end function to_upper
subroutine print_result(label, value)
character(len=*), intent(in) :: label
class(*), intent(in) :: value
select type (value)
type is (logical)
if (value) then
write(stdout, '(a,l1)') label, value
else
write(stdout, '(a,l1)') label, value
end if
type is (integer)
write(stdout, '(a,i0)') label, value
type is (character(*))
write(stdout, '(a,a)') label, value
type is (character(*), dimension(*))
write(stdout, '(a,5(a,1x))') label, value
end select
end subroutine print_result
end program string_functions