# Constant function arguments

**URL:** <https://discourse.julialang.org/t/constant-function-arguments/8649>\
**Category:** New to Julia\
**Tags:** question, proposal\
**Created:** [January 27, 2018, 11:21pm UTC](https://discourse.julialang.org/t/constant-function-arguments/8649 "2018-01-27T23:21:19Z")\
**Posts on this page:** 15\
**Page:** 1

<div class="post-metadata">

**Author:** ![SepandMeenu](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/sepandmeenu/32/8846_2.png) [@SepandMeenu](https://discourse.julialang.org/u/SepandMeenu)\
**Post date:** [January 27, 2018, 11:21pm UTC](https://discourse.julialang.org/t/constant-function-arguments/8649/1 "2018-01-27T23:21:19Z")

</div>

Is there a way to declare function arguments as constants to prevent their accidental modification in the function body?

For example,

```julia
function foo(x::const Int, y::Int)
    return x + y
end

```

or

```julia
function foo(x::immutable Int, y::Int)
    return x + y
end

```

Or even, some method like in FORTRAN, via `intent` keyword; e.g.:

```julia
function func(i) result(j)
    integer, intent(in) :: i ! input
    integer :: j ! output
    j = i **2 + i** 3
 end function func

```

---

<div class="post-metadata">

**Author:** ![stevengj](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/stevengj/32/71_2.png) [@stevengj](https://discourse.julialang.org/u/stevengj)\
**Post date:** [January 27, 2018, 11:30pm UTC](https://discourse.julialang.org/t/constant-function-arguments/8649/2 "2018-01-27T23:30:42Z")

</div>

Julia is pass-by-value, so you can’t modify the _caller’s_ `x::Int` (unlike Fortran which is pass-by-reference). There is no way to a make a local variable `const`, though (see also [https://github.com/JuliaLang/julia/issues/5148](https://github.com/JuliaLang/julia/issues/5148)).

---

<div class="post-metadata">

**Author:** ![SepandMeenu](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/sepandmeenu/32/8846_2.png) [@SepandMeenu](https://discourse.julialang.org/u/SepandMeenu)\
**Post date:** [January 27, 2018, 11:38pm UTC](https://discourse.julialang.org/t/constant-function-arguments/8649/3 "2018-01-27T23:38:14Z")

</div>

I think there is a need for a uniform declaration of an immutable variable in global and local scopes. This helps a lot for correct programming and makes Julia syntax consistent, imo, since one can now declare an `immutable struct` in Julia.  
Making immutability explicit is always a good programming practice, I believe.

---

<div class="post-metadata">

**Author:** ![Nosferican](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/nosferican/32/9275_2.png) [@Nosferican](https://discourse.julialang.org/u/Nosferican)\
**Post date:** [January 28, 2018, 7:35pm UTC](https://discourse.julialang.org/t/constant-function-arguments/8649/4 "2018-01-28T19:35:07Z")

</div>

I believe a closure might be the best alternative in many instances. See for example [Tips and tricks - Optim.jl](https://julianlsolvers.github.io/Optim.jl/latest/user/tipsandtricks/) section on dealing with constant parameters.

---

<div class="post-metadata">

**Author:** ![SepandMeenu](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/sepandmeenu/32/8846_2.png) [@SepandMeenu](https://discourse.julialang.org/u/SepandMeenu)\
**Post date:** [January 28, 2018, 9:03pm UTC](https://discourse.julialang.org/t/constant-function-arguments/8649/5 "2018-01-28T21:03:06Z")

</div>

Thanks; I’ll look into that.  
Still, I believe declaring an immutable variable should be possible in Julia.

---

<div class="post-metadata">

**Author:** ![StefanKarpinski](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/stefankarpinski/32/24_2.png) [@StefanKarpinski](https://discourse.julialang.org/u/StefanKarpinski)\
**Post date:** [January 28, 2018, 9:12pm UTC](https://discourse.julialang.org/t/constant-function-arguments/8649/6 "2018-01-28T21:12:33Z")

</div>

A pull request implementing constant local variables would be a welcomed contribution to the language!

Note on terminology: `const` and `immutable` are not the same – `const` refers to a binding which cannot be reassigned; `immutable` refers to a type whose value cannot be modified. These are orthogonal: one can have a const binding to a mutable value or a non-const binding to an immutable value.

---

<div class="post-metadata">

**Author:** ![SepandMeenu](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/sepandmeenu/32/8846_2.png) [@SepandMeenu](https://discourse.julialang.org/u/SepandMeenu)\
**Post date:** [January 29, 2018, 8:06am UTC](https://discourse.julialang.org/t/constant-function-arguments/8649/7 "2018-01-29T08:06:26Z")

</div>

thanks for the clarification. I am only a layman in that respect 😅  
My idea is simply to have compile-time _constants_, as in C++ for instance.  
But having _explicit_ immutable declaration is also a nice thing; we have now for `structs`.

---

<div class="post-metadata">

**Author:** ![Tamas\_Papp](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/tamas_papp/32/25949_2.png) [@Tamas\_Papp](https://discourse.julialang.org/u/Tamas_Papp)\
**Post date:** [January 29, 2018, 8:26am UTC](https://discourse.julialang.org/t/constant-function-arguments/8649/8 "2018-01-29T08:26:18Z")

</div>

> [@SepandMeenu](#):
>
> My idea is simply to have compile-time constants, as in C++ for instance.

I am now confused. I thought you wanted function arguments to be “constant” (ie presumably error on attempted assignment within the function scope) at runtime, with their values, of course, depending on the caller, so definitely not constant at _compile_ time.

I would really like an orthogonal feature: make `const` redefinable, via a mechanism similar to what fixed [#265](https://github.com/JuliaLang/julia/issues/265). It would be a hint to the compiler so that it can assume unchanged type and value, but redefining would trigger recompilation. (I know I can get this already via `myconstant() = value` though.)

---

<div class="post-metadata">

**Author:** ![SepandMeenu](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/sepandmeenu/32/8846_2.png) [@SepandMeenu](https://discourse.julialang.org/u/SepandMeenu)\
**Post date:** [January 30, 2018, 8:37am UTC](https://discourse.julialang.org/t/constant-function-arguments/8649/9 "2018-01-30T08:37:23Z")

</div>

You’re right, @Tamas_Papp . I am not using the precise wording. I’ll right up something more precise to convey what I mean/expect.

---

<div class="post-metadata">

**Author:** ![SepandMeenu](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/sepandmeenu/32/8846_2.png) [@SepandMeenu](https://discourse.julialang.org/u/SepandMeenu)\
**Post date:** [January 30, 2018, 10:28am UTC](https://discourse.julialang.org/t/constant-function-arguments/8649/10 "2018-01-30T10:28:22Z")

</div>

@StefanKarpinski  
I wrote up an extensive new topic about this:  
see [https://discourse.julialang.org/t/8686](https://discourse.julialang.org/t/8686)  
I hope I’ve got the idea correctly.

---

<div class="post-metadata">

**Author:** ![SepandMeenu](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/sepandmeenu/32/8846_2.png) [@SepandMeenu](https://discourse.julialang.org/u/SepandMeenu)\
**Post date:** [February 1, 2018, 4:17pm UTC](https://discourse.julialang.org/t/constant-function-arguments/8649/11 "2018-02-01T16:17:19Z")

</div>

Regarding your suggestion to use closures – if I have understood that correctly --, consider the following example:

```julia
# original function
function foo(x, y)
    return x+y
end

# generator for closures on `f`, fixes 2nd argument
function closure_gen(y)
    cl(x) = foo(x, y)
    return cl
end

# closure
bar = closure_gen(2)

# equivalent function to `bar`
baz(x) = x + 2

println( bar(1) == baz(1) ) # prints 'true': the results match

```

Let’s compare the underlying native codes:

```julia
@code_native bar(1)
#=
	.text
Filename: REPL[2]
	pushq	%rbp
	movq	%rsp, %rbp
Source line: 2
	addq	(%rdi), %rsi
	movq	%rsi, %rax
	popq	%rbp
	retq
	nopl	(%rax)
=#

```

and

```julia
@code_native baz(1)
#=
	.text
Filename: REPL[7]
	pushq	%rbp
	movq	%rsp, %rbp
Source line: 1
	leaq	2(%rdi), %rax
	popq	%rbp
	retq
	nopw	(%rax,%rax)
=#

```

Why are the generated codes different?

---

<div class="post-metadata">

**Author:** ![favba](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/favba/32/2735_2.png) [@favba](https://discourse.julialang.org/u/favba)\
**Post date:** [February 1, 2018, 4:36pm UTC](https://discourse.julialang.org/t/constant-function-arguments/8649/12 "2018-02-01T16:36:41Z")

</div>

I believe in your code the value 2 for y is not known at compile time. Only the types are known at compile time. This works as you expected:

```julia
julia> function foo(x, y)
           return x+y
       end
foo (generic function with 1 method)

julia> # generator for closures on `f`, fixes 2nd argument
       function closure_gen(y::Val{n}) where n
           cl(x) = foo(x, n)
           return cl
       end

julia> bar = closure_gen(Val{2}())
(::cl) (generic function with 1 method)

julia> bar(1)
3

julia> # equivalent function to `bar`
       baz(x) = x + 2
baz (generic function with 1 method)

julia> baz(1)
3

julia> @code_native bar(1)
	.section	__TEXT,__ text,regular,pure_instructions
Filename: REPL[15]
	pushq	%rbp
	movq	%rsp, %rbp
Source line: 3
	leaq	2(%rdi), %rax
	popq	%rbp
	retq
	nopw	(%rax,%rax)

julia> @code_native baz(1)
	.section	__TEXT,__ text,regular,pure_instructions
Filename: REPL[6]
	pushq	%rbp
	movq	%rsp, %rbp
Source line: 2
	leaq	2(%rdi), %rax
	popq	%rbp
	retq
	nopw	(%rax,%rax)

```

---

<div class="post-metadata">

**Author:** ![SepandMeenu](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/sepandmeenu/32/8846_2.png) [@SepandMeenu](https://discourse.julialang.org/u/SepandMeenu)\
**Post date:** [February 1, 2018, 4:44pm UTC](https://discourse.julialang.org/t/constant-function-arguments/8649/13 "2018-02-01T16:44:11Z")

</div>

Could you explain the meaning of `Val{n}` and `function closure_gen(y::Val{n}) where n` in your example?  
What should one do, if `y` is an `Array` or a user-defined type?

---

<div class="post-metadata">

**Author:** ![favba](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/favba/32/2735_2.png) [@favba](https://discourse.julialang.org/u/favba)\
**Post date:** [February 1, 2018, 4:51pm UTC](https://discourse.julialang.org/t/constant-function-arguments/8649/14 "2018-02-01T16:51:38Z")

</div>

This works with any `isbits` type. It will not work with a common array, but will with a `StaticArray`.

You can find more information here:  
[https://docs.julialang.org/en/stable/manual/performance-tips/#Types-with-values-as-parameters-1](https://docs.julialang.org/en/stable/manual/performance-tips/#Types-with-values-as-parameters-1)

---

<div class="post-metadata">

**Author:** ![favba](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/favba/32/2735_2.png) [@favba](https://discourse.julialang.org/u/favba)\
**Post date:** [February 1, 2018, 4:55pm UTC](https://discourse.julialang.org/t/constant-function-arguments/8649/15 "2018-02-01T16:55:07Z")

</div>

I just noticed that in my code I broke the convention stated in the manual:

_“For consistency across Julia, the call site should always pass a Valtype rather than creating an instance, i.e., use foo(Val{:bar}) rather than foo(Val{:bar}()).”_
