Skip to content

Inline more functions #13692

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 2 commits into from
Jun 25, 2024
Merged

Inline more functions #13692

merged 2 commits into from
Jun 25, 2024

Conversation

devinus
Copy link
Contributor

@devinus devinus commented Jun 25, 2024

Inline more regularly used functions in the standard Elixir modules to their Erlang STDLIB counterparts:

  • Float.to_charlist/1
  • Float.to_string/1
  • List.duplicate/2
  • List.flatten/1
  • List.flatten/2
  • Map.from_keys/2
  • Map.merge/3

Great care was taken to ensure function guards already applied to the Elixir functions were subsets of the function guards in Erlang's STDLIB. For example, Map.merge/3 specified the combiner function must be is_function(fun, 3) and Erlang's :maps.merge_with also already specifies that argument must be is_function(Combiner, 3).

The one exception to the above is the inlining of Float.to_charlist/1 and Float.to_string/1. The Elixir functions specified that the argument must be a float with is_float(float) and thus will raise a FunctionClauseError exception if e.g. an integer is passed, while :erlang.float_to_list/2 and :erlang.float_to_binary/2 will instead throw an ArgumentError exception. However, changing to the Erlang behavior brings those functions more in line with the behavior of the rest of the Elixir modules, e.g. Atom.to_charlist/1, Atom.to_string/1, Integer.to_charlist/1 and Integer.to_string/1 will all throw an ArgumentError exception on an unexpected argument type.

@josevalim
Copy link
Member

Hi @devinus, nice to see you around.

We only inline functions if they are BIFs/NIFs on the Erlang side, otherwise it is easy to end-up inlining everything. For example, if we want to optimize to List.flatten, I would rather just implement it in Elixir.

So we should only keep the maps and float ones for now, thank you.

@sabiwara
Copy link
Contributor

So we should only keep the maps and float ones for now

@josevalim I think only [:maps.from_keys/1](https://github.com/erlang/otp/blob/OTP-27.0/lib/stdlib/src/maps.erl#L167) is a BIF, :maps.merge_with/3 isn't?

@devinus
Copy link
Contributor Author

devinus commented Jun 25, 2024

@josevalim @sabiwara Updated PR with those guidelines.

Copy link
Contributor

@sabiwara sabiwara left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM! 💜

@josevalim josevalim merged commit f0fcd64 into elixir-lang:main Jun 25, 2024
9 checks passed
@josevalim
Copy link
Member

💚 💙 💜 💛 ❤️

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Development

Successfully merging this pull request may close these issues.

3 participants