Commit e0863ba6 authored by Graham, Aaron's avatar Graham, Aaron
Browse files

Merge branch 'string_expansion' into 'master'

String expansion

See merge request futility/Futility!345
parents 7a23802a 1122c982
Loading
Loading
Loading
Loading
Loading
+65 −0
Original line number Diff line number Diff line
@@ -109,6 +109,8 @@ PUBLIC :: isChar
PUBLIC :: isCharCap
PUBLIC :: isCharLow
PUBLIC :: removeDuplicates
PUBLIC :: concatenate
PUBLIC :: expandRepeatedSymbol

!> Character representing a space symbol
CHARACTER(LEN=*),PARAMETER :: BLANK=" "
@@ -1802,4 +1804,67 @@ SUBROUTINE removeDuplicates(list)

ENDSUBROUTINE removeDuplicates
!
!-------------------------------------------------------------------------------
!> @brief Concatenates an array of StringType objects into a single StringType
!> @param array the array of strings
!> @returns string the concatenated string
!>
FUNCTION concatenate(array) RESULT(string)
  TYPE(StringType),INTENT(IN) :: array(:)
  TYPE(StringType) :: string
  !
  INTEGER(SIK) :: i

  DO i=1,SIZE(array)
    string=string//array(i)
  ENDDO !i

ENDFUNCTION concatenate
!
!-------------------------------------------------------------------------------
!> @brief Expands symbols repeated in a string using a repeater symbol
!> @param string the original string
!> @returns expandedString the expanded string
!>
!> The string is assumed to be whitespace-delimited.  With this assumption, each
!> field is checked for a repeater symbol.  For example, if "*" is the delimiter,
!> the string "test 4*test2 2*1 5**test2" would expand to
!> "test test2 test2 test2 test2 1 1 5**test2". By default, @c delimiter will be "*".
!> Supplying a whitespace symbol as a delimiter will result in no modificaiton of
!> the string since it will be split on whitespace before checking for repeaters.
!>
FUNCTION expandRepeatedSymbol(string,delimiter) RESULT(expandedString)
  TYPE(StringType),INTENT(IN) :: string
  CHARACTER(LEN=*),INTENT(IN),OPTIONAL :: delimiter
  TYPE(StringType) :: expandedString
  !
  INTEGER(SIK) :: i,n
  TYPE(StringType) :: delim,nextComponent
  TYPE(StringType),ALLOCATABLE :: fields(:),repeater(:)

  delim='*'
  IF(PRESENT(delimiter)) delim=delimiter

  fields=string%split()
  DO i=1,SIZE(fields)
    repeater=fields(i)%split(CHAR(delim))
    IF(SIZE(repeater) == 2) THEN
      IF(repeater(1)%isInteger()) THEN
        n=repeater(1)%stoi()
        nextComponent=REPEAT(repeater(2)//' ',n-1)
        nextComponent=nextComponent//repeater(2)
      ELSE
        nextComponent=fields(i)
      ENDIF
    ELSE
      nextComponent=fields(i)
    ENDIF
    IF(i > 1) THEN
      expandedString=expandedString//' '
    ENDIF
    expandedString=expandedString//nextComponent
  ENDDO !i

ENDFUNCTION expandRepeatedSymbol
!
ENDMODULE IO_Strings
+40 −3
Original line number Diff line number Diff line
@@ -54,7 +54,7 @@ SUBROUTINE testIO_Strings()
  INTEGER :: stat, tmpint
  INTEGER,ALLOCATABLE :: tmpint2(:)
  REAL(SRK) :: tmpreal
  CHARACTER(LEN=32) :: char
  CHARACTER(LEN=32) :: tmpchar
  CHARACTER(LEN=52) :: test_phrase
  CHARACTER(LEN=256) :: filepath,path,fname,ext
  TYPE(StringType) :: tmpStr,tmpStr2,tmpStrArray(10)
@@ -66,8 +66,8 @@ SUBROUTINE testIO_Strings()

  COMPONENT_TEST('strarraymatch')
  DO stat=1,10
    WRITE(char,'(i32)') stat-1; char=ADJUSTL(char)
    tmpStrArray(stat)='test'//TRIM(char)
    WRITE(tmpchar,'(i32)') stat-1; tmpchar=ADJUSTL(tmpchar)
    tmpStrArray(stat)='test'//TRIM(tmpchar)
  ENDDO
  !have value 10 be the same as 9 for a duplicate/reverse test
  tmpStrArray(10)='test8'
@@ -635,6 +635,43 @@ SUBROUTINE testIO_Strings()
  ASSERT_EQ(TRIM(tmpStr),TRIM(lines(17)),'line 17')
  DEALLOCATE(tablevals,lines)

  COMPONENT_TEST('concatenate')
  tmpStrArray(1)='string 1'
  tmpStrArray(2)='string 2'
  tmpStrArray(3)='string 3'
  tmpStrArray(4)='string 4'
  tmpStrArray(5)='string 5'
  tmpStrArray(6)='string 6'
  tmpStrArray(7)='string 7'
  tmpStrArray(8)='string 8'
  tmpStrArray(9)='string 9'
  tmpStrArray(10)='string 10'
  tmpStr=concatenate(tmpStrArray)
  ASSERT_EQ(CHAR(tmpStr),\
      'string 1string 2string 3string 4string 5string 6string 7string 8string 9string 10','concatenate')
  tmpStrArray=''
  tmpStr=concatenate(tmpStrArray)
  ASSERT_EQ(CHAR(tmpStr),'','conatenate empty')
  tmpStrArray(3)='test'
  tmpStr=concatenate(tmpStrArray)
  ASSERT_EQ(CHAR(tmpStr),'test','conatenate mostly empty')

  COMPONENT_TEST('expandRepeatedSymbol')
  tmpStr='test 4*test2 2*1 5**test2'
  tmpStr2=expandRepeatedSymbol(tmpStr)
  ASSERT_EQ(CHAR(tmpStr2),'test test2 test2 test2 test2 1 1 5**test2','basic expand')
  tmpStr2=expandRepeatedSymbol(tmpStr,'**')
  ASSERT_EQ(CHAR(tmpStr2),'test 4*test2 2*1 test2 test2 test2 test2 test2','expand **')
  tmpStr='1 11 1111 111111'
  tmpStr2=expandRepeatedSymbol(tmpStr)
  ASSERT_EQ(CHAR(tmpStr2),CHAR(tmpStr),'no delim')
  tmpStr2=expandRepeatedSymbol(tmpStr,' ')
  ASSERT_EQ(CHAR(tmpStr2),CHAR(tmpStr),'whitespace delim')
  tmpStr2=expandRepeatedSymbol(tmpStr,'1')
  ASSERT_EQ(CHAR(tmpStr2),CHAR(tmpStr),'"1" delim')
  tmpStr2=expandRepeatedSymbol(tmpStr,'1111')
  ASSERT_EQ(CHAR(tmpStr2),CHAR(tmpStr),'"1111" delim')

ENDSUBROUTINE testIO_Strings
!
!-------------------------------------------------------------------------------