Type Intersection in Arrays


#1

Suppose I have a x::Vector{Any} (or another abstract type) but in fact all elements of x are Float64, then I can recover a Vector{Float64} using

y = [t for t in x]

so I don’t even need to specify what the intersection of the types in x.

It feels like there must be a more “explicit” function that achieves precisely this. Or is a comprehension in fact the recommended way?


#2

vector{Float64}([x])?


#3

map(identity, x) and identity.(x) also have the same effect, but I wouldn’t say they are qualitatively different from the comprehension.


#4

no - the point is that I don’t want to specify the type intersection!


#5

I like the identity better than the comprehension though, thank you. I’ll make this the solution until I see a better one :slight_smile:


#6

I like that. I think we should consider that standard if there isn’t one already.

It wouldn’t work for other array types however. Do we need a narrowtype function in Base? Is there such a thing? It’s perhaps telling that I’ve almost never actually found myself needing to do this.


#7

I guess with both solutions (comprehension and identity) it bothers me that it isn’t explicitly specified that a type intersection will be computed? I find myself using this patter a lot so a lot of code would break if suddenly the comprehension didn’t correctly compute the type intersection.


#8

Yes - this is exactly what I was looking for. I like that name.


#10

Just consider, that you might be considerably faster if you know the type and can specify it (e…g for convert). I guess it depends on the type of problem you are tackling and it is possible that the type recovery is not at all time critical.


#11

I don’t care about speed - I need it for dispatch


#12

Just out of shear curiosity, what are you doing that you are getting the data in Vector{Any} and then passing this to dispatch methods? I’ve been pretty happy that I seem to wind up with Vector{Any} pretty rarely (and things seem really tight in 0.7) and so rarely have to resort to fixing them.


#13

Sometimes it is just convenience that I initiate [] without worrying about the type

Sometimes I get a Vector of Basis functions of say 5 different types whichever i then split into subgroups on Whichever i can perform type stable fast operations (I don’t care about the cost of splitting)

Sometimes I actually don’t know what return values I get from some function that is given to me as parameter

It can always be avoided, but leveraging the dynamic aspects of Julia can be very convenient


#14

sorry i misread! but you could still do t = Vector{typeof(x[1]}(x)


#15

Only if there is just a single type


#16

identity.(x) doesn’t solve this either, right? Since it either promotes to a single type or to Any?

You are saying you want x = [1,2,3,4,"here"] to be promoted to Union{Int, String}?

edit: I wonder if there should be an eltypes function that returns an array of the types in a vector.


#17

At the risk of sticking my foot in my mouth (because I’m really totally ignorant as to what you’re actually doing), this sounds like a bad pattern to me that you should probably try to get out of. It sounds like these should be separate objects somehow or perhaps part of a tuple. Remember we now have named tuples in 0.7 which are really nice!

My interest in this topic comes from work I did with some IO stuff where you really don’t have proper Julia type information and have to get it (the answer is always that you need explicit metadata to explicitly set the types, and are unfortunately forced to do some compiling in the general case). My thinking was that IO is a “worst case scenario” when it comes to type stability, so if you’re having similar problems in a different application I’m definitely extremely curious about whether that’s a fundamental issue.


#18

Why is it a bad pattern if it helps to keep my code slim and simple? Or to quickly implement new ideas?


#19

If I wanted to write 100% type stable code then I don’t need Julia


#20

Well, again I don’t really know what I’m talking about, but from what you’ve said it sounds like it is inherently type unstable and results in badly typed containers. Based on my general experience in Julia I usually find that there is some way of producing type-stable (or at least producing correctly typed containers) code without too much difficulty, as Julia was designed to make this easy.

I think there are other benefits, but fair enough. It was just a suggestion (and perhaps a silly one since I don’t really know what you’re doing). The only reason I really brought it up at all is because in this thread you are asking about how to manipulate container types, so I was thinking there was probably some issue.


#21

I think for a long lived library maybe you are right - but it is not obvious. Why ignore one of the most powerful aspects of the language?