2

I want to write List.map (fun x -> x % 3) into a form like List.map ((%) 3).
The issue with the latter is that it translates to
List.map (fun x -> 3 % x) Not what I want.

Is it possible to write List.map (fun x -> x % 3). in a more succinct fashion?

Further context
New to F#. Find it nice to be able to write succinct expressions with partial applications.

E.g. for the logic add 3 to each item in list can be written just as List.map ((+) 3).

However, this doesn't apply to positional sensitive ops like division and modulus.
E.g. I read List.map ((/) 3) as - for each item in list, divide by 3.
But the actual logic is actually mapping 3 divided each item.

[12; 24; 36; 48] |> List.map ((/) 3)
// expect [4; 8; 12; 16]
// actual [3/12; 3/24; 3/36; 3/48] // type discrepancy. but just an example.

From JL0PD's answer, I think what I want is not possible with F# (at the moment).


Retrospect

What I want is not feasible due to the nature of currying/parameter positioning. E.g.
(/) 12 3 = 12 / 3  // left hand op and right hand op are equivalent.
// val it: bool = true
4
  • 1
    Interesting example of using lenses. Maybe it will allow do what you want haskellforall.com/2013/05/… Commented Apr 18, 2022 at 12:06
  • @JLOPD's answer is the best way and is long used both formally in Haskell and, informally, inf F# since you have to define flip yourself. There wont be anything else in the future. An outstanding question is as to why flip is not a formal part of the language. Commented Apr 18, 2022 at 13:31
  • @MartinFreedman, Don Syme, author of F#, several times gave talk F# code I love. He explains many decision behind language design. As another source of "why", there's history of F#, 58 pages of reflection on F# history, impact and design Commented Apr 18, 2022 at 13:50
  • Yup I am familiar with all that. It is just a pain to add flip to nearly f# project. I do agree with most of his reasoning over <| and not having >| and <| in one line, but flip solves that. Commented Apr 18, 2022 at 13:54

2 Answers 2

4

Common workaround for functions that have incorrect order of parameters is flip function

let flip f x y = f y x

With this function you can write

List.map (flip (%) 3)

A bit less universal, but more clear is to create specialized function, like mod

let mod y x = x % y
List.map (mod 3)

But I don't think that that's increases readability and/or maintainability. I would use current version instead

Sign up to request clarification or add additional context in comments.

1 Comment

I would not say it is an incorrect order of arguments, just not the desired order for the case at hand. This is a common issue in functional programming hence the need for a function to reverse arguments.
1

I fully agree with JL0PD' answer . One more alternative is that you can define your own operator. i.e.

let (%.) x y = y % x 
[12; 24; 36; 48] |> List.map ((%.) 3)

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.