# Robert Petkus - test some of the features of Julia
# Found these links helpful:
# Multiple dispatch: a function can have different behaviors depending on the types of its arguments
function f(x::Int, y::Int) # f for two integers
return x + y
end
function f(x::String, y::String) # f for two strings
return x * y # string concatenation
end
function f(x::Float64, y::Float64) # f for two floats
return x / y # floating-point division
end
# Parametric polymorphism: a function can be defined for a range of types using type parameters
function g(x::T, y::T) where {T<:Number} # g for any subtype of Number
return x - y
end
# Direct calling of Fortran libraries: a function can call an external Fortran subroutine using ccall
function h(n::Int) # h for an integer
# call the dgesv subroutine from LAPACK to solve a linear system Ax = b
A = rand(n, n) # create a random n x n matrix A
b = rand(n) # create a random n-vector b
ipiv = zeros(Int32, n) # create an array of pivot indices
info = Ref{Int32}() # create a reference to store the return code
ccall( (:dgesv_, "liblapack"), Cvoid,
(Ref{Int32}, Ref{Int32}, Ptr{Float64}, Ref{Int32}, Ptr{Int32}, Ptr{Float64}, Ref{Int32}, Ref{Int32}),
n, 1, A, n, ipiv, b, n, info ) # call the subroutine with appropriate arguments and types
return (info[], b) # return the return code and the solution vector b (overwritten by dgesv)
end
# Random stuff - test functions with some examples
println(f(2, 3)) # 5
println(f("Hello", "World")) # HelloWorld
println(f(4.0, 2.0)) # 2.0
println(g(10, 3)) # 7
println(g(3.14, 2.71)) # 0.42999999999999994
info, x = h(5) # solve a 5 x 5 linear system
println(info) # 0 (success)
println(x) # the solution vector