[Haskell-beginners] find by

Julian Arni julian at edx.org
Wed May 15 20:37:23 CEST 2013


Thanks a lot for the response.

Yeah, I noticed that a function f :: [a] -> a needn't return an
element of the list (sum, for instance, rarely does), and so from that
perspective I shouldn't be too hopeful. But it doesn't seem all that
pleasant, and probably will be quite repetitive, otherwise. The actual
fn I have is:

  fFirst = (head .) . intersect    -- Some empty-list checks around it
too, but they're irrelevant for exposition

One of the lists fFirst takes as argument - call it xs - shows up, in
basically a 'zipped' format in other lists (i.e., map fst, map snd,
etc. over those lists is xs). The other list - call is ys - only
exists as a simple list (not of tuples). So yeah,

  fNew = head $ filter (\(_,x) -> x `elem` ys)

Would work, I suppose. But the ugly thing is that for each n, given a
list of n-tuples s.t. mapping (\(_,)^n x -> x) over the list returns
my original xs [where here (_,)^n is meta-speak for _, repeated n
times], not only do I have to rewrite this (which I half-expect, given
that I'm working with tuples), but calculations which are intuitively
'the same' are going to have to be done multiple times (I think). It
looks ugly and inefficient.

(P.S.: Might there be some html/mime issues in the list archive?
Possibly some characters aren't properly escaped - I don't really know
- but in the archive my previous emails were all truncated).

On Wed, May 15, 2013 at 2:03 PM, Brent Yorgey <byorgey at seas.upenn.edu> wrote:
> On Wed, May 15, 2013 at 01:09:37PM -0400, Julian Arni wrote:
>> (Truncated again - trying plain text. Sorry for the spam.)
>>
>> I have a function that, simplifying a little, looks like this:
>>
>>   fn :: [a] -> a
>>   fn = (head .) . takeWhile $ (\_ -> True)
>>
>> From this, I want a function with the signature fn' :: [(x,a)] ->
>> (x,a) such that:
>>
>>     snd $ fn' (zip [x] [a]) = fn [a]
>>
>> I can see ways of doing this by altering fn, or by repeating some of
>> fn in the definition of fn', or (because in this case I know that if
>> fn xs = x, fn is returning the first x in xs and not any others), by
>> doing something nasty like:
>>
>>   fn' xs = xs !! fromMaybe 0 (findIndex (\(_,a) -> a == fn (snd $
>> unzip xs)) xs )
>>
>> But it seems to me like there should be prettier solutions to this
>> (that do not involve changing the definition of fn). After all, this
>> doesn't seem like a rare pattern.
>>
>> Anyone know if in fact there's a better way to go about it?
>
> This is not possible.  The problem is that given
>
>   fn :: [A] -> A
>
> there is no way to tell where it found the particular value of type A
> in the list (unless, as you say, you happen to know something extra
> about the A's and how the function works).  And since it takes
> specifically a list of type A, there is no way to give it a list with
> some "extra" information tagged onto the A's.  Your only option is to
> generalize fn somehow.
>
> You say "this doesn't seem like a rare pattern"; as a counterpoint, I
> don't think I have ever wanted it.  A function with the type of fn
> does not seem very useful -- what should it do on the empty list?  And
> why not just use something like 'find' directly?
>
> -Brent
>
> _______________________________________________
> Beginners mailing list
> Beginners at haskell.org
> http://www.haskell.org/mailman/listinfo/beginners



More information about the Beginners mailing list