split Subroutine

private pure subroutine split(self, tokens, sep, max_tokens)

Return a list of substring in the string, using sep as the delimiter string.

 type(string)              :: astring
 type(string), allocatable :: strings(:)
 logical                   :: test_passed(11)
 astring = '+ab-++cre-++cre-ab+'
 call astring%split(tokens=strings, sep='+')
 test_passed(1) = (strings(1)//''=='ab-'.and.strings(2)//''=='cre-'.and.strings(3)//''=='cre-ab')
 astring = 'ab-++cre-++cre-ab+'
 call astring%split(tokens=strings, sep='+')
 test_passed(2) = (strings(1)//''=='ab-'.and.strings(2)//''=='cre-'.and.strings(3)//''=='cre-ab')
 astring = 'ab-++cre-++cre-ab'
 call astring%split(tokens=strings, sep='+')
 test_passed(3) = (strings(1)//''=='ab-'.and.strings(2)//''=='cre-'.and.strings(3)//''=='cre-ab')
 astring = 'Hello '//new_line('a')//'World!'
 call astring%split(tokens=strings, sep=new_line('a'))
 test_passed(4) = (strings(1)//''=='Hello '.and.strings(2)//''=='World!')
 astring = 'Hello World!'
 call astring%split(tokens=strings)
 test_passed(5) = (strings(1)//''=='Hello'.and.strings(2)//''=='World!')
 astring = '+ab-'
 call astring%split(tokens=strings, sep='+')
 test_passed(6) = (strings(1)//''=='ab-')
 astring = '+ab-'
 call astring%split(tokens=strings, sep='-')
 test_passed(7) = (strings(1)//''=='+ab')
 astring = '+ab-+cd-'
 call astring%split(tokens=strings, sep='+')
 test_passed(8) = (strings(1)//''=='ab-'.and.strings(2)//''=='cd-')
 astring = 'ab-+cd-+'
 call astring%split(tokens=strings, sep='+')
 test_passed(9) = (strings(1)//''=='ab-'.and.strings(2)//''=='cd-')
 astring = '+ab-+cd-+'
 call astring%split(tokens=strings, sep='+')
 test_passed(10) = (strings(1)//''=='ab-'.and.strings(2)//''=='cd-')
 astring = '1-2-3-4-5-6-7-8'
 call astring%split(tokens=strings, sep='-', max_tokens=3)
 test_passed(11) = (strings(1)//''=='1'.and.strings(2)//''=='2'.and.strings(3)//''=='3'.and.strings(4)//''=='4-5-6-7-8')
 print '(L1)', all(test_passed)

Type Bound

string

Arguments

Type IntentOptional Attributes Name
class(string), intent(in) :: self

The string.

type(string), intent(out), allocatable :: tokens(:)

Tokens substring.

character(kind=CK, len=*), intent(in), optional :: sep

Separator.

integer, intent(in), optional :: max_tokens

Fix the maximum number of returned tokens.


Calls

proc~~split~~CallsGraph proc~split stringifor_string_t::string%split proc~partition stringifor_string_t::string%partition proc~split->proc~partition proc~unique stringifor_string_t::string%unique proc~split->proc~unique raw raw proc~partition->raw proc~replace stringifor_string_t::string%replace proc~unique->proc~replace proc~replace_one_occurrence stringifor_string_t::string%replace_one_occurrence proc~replace->proc~replace_one_occurrence

Called by

proc~~split~~CalledByGraph proc~split stringifor_string_t::string%split proc~camelcase stringifor_string_t::string%camelcase proc~camelcase->proc~split proc~glob_string stringifor_string_t::string%glob_string proc~glob_string->proc~split proc~snakecase stringifor_string_t::string%snakecase proc~snakecase->proc~split proc~split_chunked stringifor_string_t::string%split_chunked proc~split_chunked->proc~split proc~startcase stringifor_string_t::string%startcase proc~startcase->proc~split proc~write_lines~2 stringifor_string_t::string%write_lines proc~write_lines~2->proc~split interface~glob stringifor_string_t::glob interface~glob->proc~glob_string proc~glob_character stringifor_string_t::string%glob_character interface~glob->proc~glob_character proc~write_file~2 stringifor_string_t::string%write_file proc~write_file~2->proc~write_lines~2 proc~glob_character->interface~glob program~volatile_doctest~16 volatile_doctest program~volatile_doctest~16->interface~glob program~volatile_doctest~69 volatile_doctest program~volatile_doctest~69->interface~glob program~volatile_doctest~80 volatile_doctest program~volatile_doctest~80->interface~glob

Contents

Source Code


Source Code

   pure subroutine split(self, tokens, sep, max_tokens)
   !< Return a list of substring in the string, using sep as the delimiter string.
   !<
   !< @note Multiple subsequent separators are collapsed to one occurrence.
   !<
   !< @note If `max_tokens` is passed the returned number of tokens is either `max_tokens` or `max_tokens + 1`.
   !<
   !<```fortran
   !< type(string)              :: astring
   !< type(string), allocatable :: strings(:)
   !< logical                   :: test_passed(11)
   !< astring = '+ab-++cre-++cre-ab+'
   !< call astring%split(tokens=strings, sep='+')
   !< test_passed(1) = (strings(1)//''=='ab-'.and.strings(2)//''=='cre-'.and.strings(3)//''=='cre-ab')
   !< astring = 'ab-++cre-++cre-ab+'
   !< call astring%split(tokens=strings, sep='+')
   !< test_passed(2) = (strings(1)//''=='ab-'.and.strings(2)//''=='cre-'.and.strings(3)//''=='cre-ab')
   !< astring = 'ab-++cre-++cre-ab'
   !< call astring%split(tokens=strings, sep='+')
   !< test_passed(3) = (strings(1)//''=='ab-'.and.strings(2)//''=='cre-'.and.strings(3)//''=='cre-ab')
   !< astring = 'Hello '//new_line('a')//'World!'
   !< call astring%split(tokens=strings, sep=new_line('a'))
   !< test_passed(4) = (strings(1)//''=='Hello '.and.strings(2)//''=='World!')
   !< astring = 'Hello World!'
   !< call astring%split(tokens=strings)
   !< test_passed(5) = (strings(1)//''=='Hello'.and.strings(2)//''=='World!')
   !< astring = '+ab-'
   !< call astring%split(tokens=strings, sep='+')
   !< test_passed(6) = (strings(1)//''=='ab-')
   !< astring = '+ab-'
   !< call astring%split(tokens=strings, sep='-')
   !< test_passed(7) = (strings(1)//''=='+ab')
   !< astring = '+ab-+cd-'
   !< call astring%split(tokens=strings, sep='+')
   !< test_passed(8) = (strings(1)//''=='ab-'.and.strings(2)//''=='cd-')
   !< astring = 'ab-+cd-+'
   !< call astring%split(tokens=strings, sep='+')
   !< test_passed(9) = (strings(1)//''=='ab-'.and.strings(2)//''=='cd-')
   !< astring = '+ab-+cd-+'
   !< call astring%split(tokens=strings, sep='+')
   !< test_passed(10) = (strings(1)//''=='ab-'.and.strings(2)//''=='cd-')
   !< astring = '1-2-3-4-5-6-7-8'
   !< call astring%split(tokens=strings, sep='-', max_tokens=3)
   !< test_passed(11) = (strings(1)//''=='1'.and.strings(2)//''=='2'.and.strings(3)//''=='3'.and.strings(4)//''=='4-5-6-7-8')
   !< print '(L1)', all(test_passed)
   !<```
   !=> T <<<
   class(string),             intent(in)           :: self           !< The string.
   type(string), allocatable, intent(out)          :: tokens(:)      !< Tokens substring.
   character(kind=CK, len=*), intent(in), optional :: sep            !< Separator.
   integer,                   intent(in), optional :: max_tokens     !< Fix the maximum number of returned tokens.
   character(kind=CK, len=:), allocatable          :: sep_           !< Separator, default value.
   integer                                         :: No             !< Number of occurrences of sep.
   integer                                         :: t              !< Character counter.
   type(string)                                    :: temporary      !< Temporary storage.
   type(string), allocatable                       :: temp_toks(:,:) !< Temporary tokens substring.

   if (allocated(self%raw)) then
     sep_ = SPACE ; if (present(sep)) sep_ = sep

     temporary = self%unique(sep_)
     No = temporary%count(sep_)

     if (No>0) then
       if (present(max_tokens)) then
         if (max_tokens < No.and.max_tokens > 0) No = max_tokens
       endif
       allocate(temp_toks(3, No))
       temp_toks(:, 1) = temporary%partition(sep_)
       if (No>1) then
         do t=2, No
           temp_toks(:, t) = temp_toks(3, t-1)%partition(sep_)
         enddo
       endif

       if (temp_toks(1, 1)%raw/=''.and.temp_toks(3, No)%raw/='') then
         allocate(tokens(No+1))
         do t=1, No
           if (t==No) then
             tokens(t  ) = temp_toks(1, t)
             tokens(t+1) = temp_toks(3, t)
           else
             tokens(t) = temp_toks(1, t)
           endif
         enddo
       elseif (temp_toks(1, 1)%raw/='') then
         allocate(tokens(No))
         do t=1, No
           tokens(t) = temp_toks(1, t)
         enddo
       elseif (temp_toks(3, No)%raw/='') then
         allocate(tokens(No))
         do t=1, No-1
           tokens(t) = temp_toks(1, t+1)
         enddo
         tokens(No) = temp_toks(3, No)
       else
         allocate(tokens(No-1))
         do t=2, No
           tokens(t-1) = temp_toks(1, t)
         enddo
       endif

     else
       allocate(tokens(1))
       tokens(1) = self
     endif
   endif
   endsubroutine split