Task: Sum to 100








VB: 
Function plusOne(iAry() As Integer, spot As Integer) As Integer
    Dim spotLim As Integer = If(spot = 0, 1, 2) 
    If iAry(spot) = spotLim Then 
        If spot = 0 Then Return -1 
        iAry(spot) = 0 
        Return plusOne(iAry, spot - 1) 
    Else
        iAry(spot) += 1 
    End If
    Return spot
End Function


Function generate(iAry() As Integer, terms As String) As String
    Dim operations As String() = {"", "-", "+"} 
    generate = ""
    For i As Integer = 0 To iAry.Count - 1
        generate &= operations(iAry(i)) & Mid(terms, i + 1, 1).ToString()
    Next
End Function


Function eval(sequence As String) As Integer
    eval = 0
    Dim term As Integer = 0, operation As Integer = 1
    For Each ch As Char In sequence
        Select Case ch
            Case "-", "+" 
                eval += If(operation = 0, -term, term) : term = 0 
                operation = If(ch = "-", 0, 1) 
            Case Else 
                term = term * 10 + Val(ch)
        End Select
    Next
    eval += If(operation = 0, -term, term) 
End Function


Sub reSort(ByRef first As List(Of Integer), ByRef second As List(Of Integer))
    Dim lou As New List(Of ULong) 
    For i As Integer = 0 To first.Count - 1
        lou.Add((CULng(first(i)) << 32) + second(i)) 
    Next
    lou.Sort()
    For k As Integer = 0 To first.Count - 1
        first(k) = lou(k) >> 32 
        second(k) = lou(k) And &H7FFFFFFF 
    Next
End Sub



Function firstMiss(loi As List(Of Integer))
    Dim low As Integer = 0, high As Integer = loi.Count - 1, middle = (low + high) \ 2
    Do
        If loi(middle) = middle Then low = middle + 1 Else high = middle - 1
        middle = (low + high) \ 2
    Loop Until high <= low
    Return middle + If(loi(middle) = middle, 1, 0)
End Function



Sub Solve100(Optional terms As String = "123456789",
             Optional targSum As Integer = 100,
             Optional highNums As Integer = 10)
    Dim lastDig As Integer = Len(terms) - 1 
    Dim iAry() As Integer = New Integer(lastDig) {} 
    Dim seq As String 
    Dim sVal As Integer 
    Dim sCnt As Integer = 1 
    Dim res As New List(Of Integer) 
    Dim tally As New List(Of Integer) 
    Console.WriteLine("List of solutions that evaluate to 100:")
    Do 
        seq = generate(iAry, terms) 
        sVal = eval(seq) 
        If sVal >= 0 Then 
            If res.Contains(sVal) Then tally(res.IndexOf(sVal)) += 1 _
                                  Else res.Add(sVal) : tally.Add(1)
            If sVal = targSum Then _
                Console.WriteLine(" {0,2} {1}", sCnt, seq) : sCnt += 1
        End If
    Loop Until plusOne(iAry, lastDig) < 0
    reSort(tally, res) 
    Console.WriteLine("The sum that has the the most solutions is {0}, (at {1}).",
                      res.Last, tally.Last)
    reSort(res, tally) 
    Console.WriteLine("The lowest positive sum that can
                      firstMiss(res))
    Console.WriteLine("The ten highest numbers that can be expressed are:")
    res.Reverse() 
    sCnt = 0 
    For Each item As Integer In res.Take(highNums)
        Console.Write("{0, -11}", item)
        sCnt = (sCnt + 1) Mod 5 : If sCnt = 0 Then Console.WriteLine()
    Next
End Sub

Sub Main()
    Solve100() 
End Sub



Fortran: 









program sumto100
    
    parameter (nexpr = 13122)

    print *
    print *, 'Show all solutions that sum to 100'
    print *
    do i = 0, nexpr-1
        if ( ievaluate(i) .eq. 100 ) then
            call printexpr(i)
        endif    
    enddo
    
    print *
    print *, 'Show the sum that has the maximum number of solutions'
    print *    
    ibest = -1
    nbest = -1
    do i = 0, nexpr-1
        itest = ievaluate(i)
        if ( itest .ge. 0 ) then
            ntest = 0
            do j = 0, nexpr-1
                if ( ievaluate(j) .eq. itest ) then
                    ntest = ntest + 1
                endif
            enddo
            if ( (ntest .gt. nbest) ) then
                ibest = itest
                nbest = ntest
            endif
        endif
    enddo
    print *, ibest, ' has ', nbest, ' solutions'
    print *






    print *
    print *, 'Show the lowest positive number that can''t be expressed'
    print *
    loop: do i = 0,123456789
        do j = 0,nexpr-1
            if ( i .eq. ievaluate(j) ) then
                cycle loop
            endif
        enddo
        exit
    enddo loop
    print *, i
 
    print *
    print *, 'Show the ten highest numbers that can be expressed'
    print *
    ilimit = 123456789
    do i = 1,10
        ibest = 0
        do j = 0, nexpr-1
            itest = ievaluate(j)
            if ( (itest .le. ilimit) .and. (itest .gt. ibest ) ) then
                ibest = itest
            endif
        enddo
        do j = 0, nexpr-1    
            if ( ievaluate(j) .eq. ibest ) then
                call printexpr(j)
            endif    
        enddo
        ilimit = ibest - 1;
    enddo
       
end 

function ievaluate(icode)
    ic = icode
    ievaluate = 0
    n = 0
    ip = 1
    do k = 9,1,-1
        n = ip*k + n
        select case(mod(ic,3))
            case ( 0 )
                ievaluate = ievaluate + n
                n = 0
                ip = 1
            case ( 1 )
                ievaluate = ievaluate - n
                n = 0
                ip = 1
            case ( 2 )
                ip = ip * 10
        end select
        ic = ic / 3                
    enddo
end 

subroutine printexpr(icode)
    character(len=32) s
    ia = 19683
    ib =  6561
    s = ""
    do k = 1,9
        ic = mod(icode,ia) / ib
        ia = ib
        ib = ib / 3
        select case(mod(ic,3))
            case ( 0 )
                if ( k .gt. 1 ) then
                    s = trim(s) // '+'
                endif
            case ( 1 )
                s = trim(s) // '-'
        end select
        s = trim(s) // char(ichar('0')+k)
    end do
    ivalue = ievaluate(icode)
    print *, ivalue, ' = ', s
end