If I understand your question, you want to accept e.g. both 
    [Foo{Int,2}((1,2)), Foo{Int,2)((2,3))] and [Foo{Int,2}((1,2)), 
Foo{Int,3)((2,3,4)) ] and then do something with them, 
and you want to reject e.g.
    [Foo{Int,2((1,2)), Foo{Float64,2}((2.0,3.0))].

Having two method signatures that share a common functional body does not 
seem like too much of an imposition.
Using an abstract type lets the common body be more narrowly typed.

abstract AbstractFoo
type Foo{T,N} <: AbstractFoo
    a::NTuple{N,T}
end

function bar{T,N}(x::Vector{Foo{T,N}}) = babar(x)
function bar{T}(x::Vector{Foo{T}})     = babar(x)

function babar{T<:AbstractFoo}(x::Vector{T})
   all_the_things_to_do_with_Foos(x)
end

    

On Monday, April 4, 2016 at 4:46:21 PM UTC-4, Davide Lasagna wrote:
>
> Thanks, yes, I have tried this, but did not mention what happens.
>
> For the signature you suggest, you get a `MethodError` in the case the 
> vector `x` is homogeneous in both parameters.
>
> Look at this code
>
> type Foo{T, N}
>     a::NTuple{N, T}
> end
>
> function make_homogeneous_Foos(M)
>     fs = Foo{Float64, 2}[]
>     for i = 1:M
>         f = Foo{Float64, 2}((0.0, 0.0))
>         push!(fs, f)
>     end
>     fs
> end
>
> function bar{T}(x::Vector{Foo{T}})
>     println("Hello, Foo!")
> end
>
> const fs = make_homogeneous_Foos(100)
>
> bar(fs)
>
> which results in 
>
> ERROR: LoadError: MethodError: `bar` has no method matching 
> bar(::Array{Foo{Float64,2},1})
>
> A workaround would be to have two methods, one for the homogeneous 
> elements in the first parameter, as you suggest, and a second for a vector 
> with homogeneous elements in both parameters, with both T, N specified in 
> the signature. But I have to write an extra method...
>
>
> On Monday, April 4, 2016 at 9:32:55 PM UTC+1, John Myles White wrote:
>>
>> Vector{Foo{T}}?
>>
>> On Monday, April 4, 2016 at 1:25:46 PM UTC-7, Davide Lasagna wrote:
>>>
>>> Hi all, 
>>>
>>> Consider the following example code
>>>
>>> type Foo{T, N}
>>>     a::NTuple{N, T}
>>> end
>>>
>>> function make_Foos(M)
>>>     fs = Foo{Float64}[]
>>>     for i = 1:M
>>>         N = rand(1:2)
>>>         f = Foo{Float64, N}(ntuple(i->0.0, N))
>>>         push!(fs, f)
>>>     end
>>>     fs
>>> end
>>>
>>> function bar{F<:Foo}(x::Vector{F})
>>>     println("Hello, Foo!")
>>> end
>>>
>>> const fs = make_Foos(100)
>>>
>>> bar(fs)
>>>
>>> What would be the signature of `bar` to enforce that all the entries of 
>>> `x` have the same value for the first parameter T? As it is now, `x` could 
>>> contain an `Foo{Float64}` and a `Foo{Int64}`, whereas I would like to 
>>> enforce homogeneity of the vector elements in the first parameter.
>>>
>>> Thanks
>>>
>>>
>>>

Reply via email to