# Getting this type signature correct

**URL:** <https://discourse.julialang.org/t/getting-this-type-signature-correct/90383>\
**Category:** General Usage\
**Created:** [November 17, 2022, 4:33am UTC](https://discourse.julialang.org/t/getting-this-type-signature-correct/90383 "2022-11-17T04:33:22Z")\
**Posts on this page:** 4\
**Page:** 1

<div class="post-metadata">

**Author:** ![torrance](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/torrance/32/38990_2.png) [@torrance](https://discourse.julialang.org/u/torrance)\
**Post date:** [November 17, 2022, 4:33am UTC](https://discourse.julialang.org/t/getting-this-type-signature-correct/90383/1 "2022-11-17T04:33:22Z")

</div>

Say I have a function that accepts _at least_ one argument of `Union{Int, Colon, OrdinalRange}`. I can write this like:

```julia
function test(i::Union{Int, Colon, OrdinalRange}, I::Union{Int, Colon, OrdinalRange}...)
    println((i, I...))
end

```

But that’s a tad verbose. I _could_ obviously create a typedef for the Union, but let’s say this is a one-off function and I’d rather avoid polluting my namespace. So I tried:

```julia
function test(I::P, I::P...) where P <: Union{Int, Colon, OrdinalRange}
    println((i, I...))
end

```

However, this fails with `MethodError` when called with 2 arguments. For example, if I call `test(1, 2)`, this correctly matches on the first argument, but not on the second argument.

Why is this?

---

<div class="post-metadata">

**Author:** ![CameronBieganek](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/cameronbieganek/32/6915_2.png) [@CameronBieganek](https://discourse.julialang.org/u/CameronBieganek)\
**Post date:** [November 17, 2022, 4:42am UTC](https://discourse.julialang.org/t/getting-this-type-signature-correct/90383/2 "2022-11-17T04:42:12Z")

</div>

When I use your second definition, `test(1, 2)` works for me, but `test(1, :)` does not:

```julia
julia> function test(i::P, I::P...) where P <: Union{Int, Colon, OrdinalRange}
           println((i, I...))
       end
test (generic function with 1 method)

julia> test(1, 2)
(1, 2)

julia> test(1, :)
ERROR: MethodError: no method matching test(::Int64, ::Colon)
Closest candidates are:
  test(::P, ::P...) where P<:Union{Colon, Int64, OrdinalRange} at REPL[2]:1

```

The reason is because the second definition declares that all the arguments are of the same type `P`. So your second definition is not equivalent to the first definition, because in your first definition the arguments can be of different types.

---

<div class="post-metadata">

**Author:** ![torrance](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/torrance/32/38990_2.png) [@torrance](https://discourse.julialang.org/u/torrance)\
**Post date:** [November 17, 2022, 4:43am UTC](https://discourse.julialang.org/t/getting-this-type-signature-correct/90383/3 "2022-11-17T04:43:19Z")

</div>

Duh. Yes, of course! Thanks for that @CameronBieganek!

---

<div class="post-metadata">

**Author:** ![CameronBieganek](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/cameronbieganek/32/6915_2.png) [@CameronBieganek](https://discourse.julialang.org/u/CameronBieganek)\
**Post date:** [November 17, 2022, 4:46am UTC](https://discourse.julialang.org/t/getting-this-type-signature-correct/90383/4 "2022-11-17T04:46:04Z")

</div>

By the way, you can use a `let` block if you want to have a local type alias that doesn’t pollute your namespace:

```julia
julia> let
           T = Union{Int, Colon, OrdinalRange}
           global foo(x::T, y::T...) = (x, y)
       end
foo (generic function with 1 method)

julia> foo(1, :)
(1, (Colon(),))

julia> T
ERROR: UndefVarError: T not defined

```

Though in this case I would probably just write it out the long way.
