view julia/dp.jl @ 14:c6bc1d41657c

DP exercises in Julia
author Lewin Bormann <lbo@spheniscida.de>
date Fri, 24 Feb 2023 23:31:00 +0100
parents
children be208ce0ffaf
line wrap: on
line source


function largest_plus(a::AbstractMatrix{Bool})::Int
    is_still_plus(i, j, n) = (i+n) <= size(a, 1) && (i-n) >= 1 && (j+n) <= size(a, 2) && (j-n) >= 1 && a[i,j] && a[i+n,j] && a[i-n,j] && a[i,j+n] && a[i,j-n]
    is_plus_center(i, j) = is_still_plus(i, j, 1)

    initial_centers = [(i, j) for i = 2:size(a, 1)-1 for j = 2:size(a, 2)-1 if is_plus_center(i, j)]

    centers = initial_centers
    for n = 2:size(a, 1)
        new_centers = [(i, j) for (i, j) = centers if is_still_plus(i, j, n)]
        if isempty(new_centers)
            return n-1
        end
        centers = new_centers
    end
    -1
end

"""
ACDB is interleaving of AB and CD
 
ADEBCF is interleaving of ABC and DEF
 
ACBCD is interleaving of ABC and CD
 
ACDABC is interleaving of ABC and ACD
"""
function string_is_interleaving(a::AbstractString, b::AbstractString, c::AbstractString)::Bool
    if length(a) == 0 && length(b) == 0 && length(c) == 0
        true
    else
        if !isempty(a) && a[begin] == c[begin]
            if length(a) == 1 && length(b) == 0
                length(c) == 1
            else
                string_is_interleaving(a[2:end], b, c[2:end])
            end
        elseif !isempty(b) && b[begin] == c[begin]
            if length(b) == 1 && length(a) == 0
                length(c) == 1
            else
                string_is_interleaving(a, b[2:end], c[2:end])
            end
        else
            false
        end
    end
end

function partition_3(s::AbstractSet{T}, s1=nothing, s2=nothing, s3=nothing, n=length(s)) where {T<:Integer}
    if isnothing(s1) || isnothing(s2) || isnothing(s3)
        s1, s2, s3 = Set{T}(), Set{T}(), Set{T}()
    end
    if length(s1) > 0 && length(s2) > 0 && length(s3) > 0 && length(s1)+length(s2)+length(s3) == n && sum(s1) == sum(s2) && sum(s2) == sum(s3)
        return (true, (s1, s2, s3))
    elseif isempty(s)
        return (false, (s1,s2,s3))
    end

    e = pop!(s)

    push!(s1, e)
    ok, sets = partition_3(s, s1, s2, s3, n)
    if ok
        return ok, sets
    end

    pop!(s1, e)
    push!(s2, e)
    ok, sets = partition_3(s, s1, s2, s3, n)
    if ok
        return ok, sets
    end

    pop!(s2, e)
    push!(s3, e)
    ok, sets = partition_3(s, s1, s2, s3, n)
    if ok
        return ok, sets
    end

    pop!(s3, e)
    push!(s, e)

    return false, (s1, s2, s3)
end

function total_possible_solutions(coefficients::AbstractVector{<:Integer}, rhs::Integer)::Int
    if isempty(coefficients)
        return rhs == 0 ? 1 : 0
    end
    c = 0
    for v = 0:rhs
        c += total_possible_solutions((@view coefficients[2:end]), rhs-coefficients[begin]*v)
    end
    c
end

function number_of_pattern_times(hs::AbstractString, pat::AbstractString)::Int
    if isempty(pat) || isempty(hs)
        0
    else
        if length(pat) == 1
            c = hs[begin] == pat[begin] ? 1 : 0
            c + number_of_pattern_times((@view hs[2:end]), pat)
        else
            if hs[begin] == pat[begin]
                number_of_pattern_times((@view hs[2:end]), (@view pat[2:end])) + number_of_pattern_times((@view hs[2:end]), pat)
            else
                number_of_pattern_times((@view hs[2:end]), pat)
            end
        end
    end
end