The first call works because Range is an Enumerable, and since getting the first element is an act of enumeration. On the other hand, sample needs to know the full list to do what it is doing, so can't be seen as an act of enumeration.
For example, first would work with an unbounded enumerable, but there is no way sample could:
I think conceptually .first() is not the same as .sample(). At the least when I read
it, I would assume that .first() yields the first five elements (if the argument is
5), whereas .sample() should probably return 5 random elements. Not sure if others
read it the same way, but that was my initial impression.
Even if limited to bound Range, we can't enumerate all possible elements in Float.
As in the first proposal, it would make sense only for Integer ranges.