kamaroly

kamaroly

Elixir is sorting map by key name in ascending order, but I don’t want this behaviour. It is causing me to have undesired reports output. I’d like to have the employee number and names to begin, then followed by leave types instead of the following.

Is there a way to rearrange the map by key in Elixir, so that

records = [
  %{
    "Annual Leave" => "0",
    "Compassionate" => "0",
    "Maternity" => "0",
    "Paternity" => "0",
    "Paternity Leave" => "0",
    "Sick Leave" => 0,
    "Study Leave" => 0,
    "emp_no" => "EMP0004",
    "names" => "Benard Kipucho"
  },
  %{
    "Annual Leave" => "87",
    "Compassionate" => 0,
    "Maternity" => 0,
    "Paternity" => 0,
    "Paternity Leave" => "1024",
    "Sick Leave" => "100",
    "Study Leave" => "989",
    "emp_no" => "EMP001",
    "names" => "Kamaro Lambert"
  }
]

# SOMETHING LIKE THIS CAN make the map starts with emp_no and names.
Enum.map_key_starts_with(records, ["emp_no", "names"])

The above should give the following results

[
  %{
    
    "emp_no" => "EMP0004", # Shifted to the starting point
    "names" => "Benard Kipucho", # Shifted to the starting point
    "Annual Leave" => "0",
    "Compassionate" => "0",
    "Maternity" => "0",
    "Paternity" => "0",
    "Paternity Leave" => "0",
    "Sick Leave" => 0,
    "Study Leave" => 0
  },
  %{
    "emp_no" => "EMP001", # Shifted to the starting point
    "names" => "Kamaro Lambert",# Shifted to the starting point
    "Annual Leave" => "87",
    "Compassionate" => 0,
    "Maternity" => 0,
    "Paternity" => 0,
    "Paternity Leave" => "1024",
    "Sick Leave" => "100",
    "Study Leave" => "989"
  }
]

Showing Posts 1 to 10

cmo

cmo

If you need sorted keys then a Map is the wrong data structure. There are lists, keyword lists, records, custom data structures, etc.

Search for “map with ordered keys” as this has been discussed on here a few times.

NobbZ

NobbZ

Have you considered using structs with a custom inspection protocol implementation?

Maps with string keys deep into the program always smell.

LostKobrakai

LostKobrakai

Maps are an unordered dataformat. The BEAM just has a default sort order given it has a global ordering between any term it can represent, which is used to order things where they need to become ordered. So the solution here is to use a datatype which does retain order (lists) instead of maps.

For your usecase I’d even argue that this is a pure view layer concern – as in how data is presented – so your view layer code could simply order the columns as needed before rendering the data.

kamaroly

kamaroly OP

I haven’t tried this. It looks like I just need to use lists.

kamaroly

kamaroly OP

It’s not entirely a view issue. I have a pivot table module I pass any list of map and specify what should be rows, colum to transpose and colum to use as value for sum, count etc… then I render it as html, csv, pdf etc… to download or render in a browser.

I will try with lists and see how it works. So far it looks like a list of tuples maintains the order.

NobbZ

NobbZ

Sounds like presentation layer…

stevensonmt

stevensonmt

I always seem to struggle with choosing the right data structure for modeling data. My (probably naive) way of thinking about it that maps are for data that will need fast insert, fast retrieval, and fast updates but for which order is not (as) important. Lists (including keyword lists) are for things that need fast appends, LIFO order is important, random access does not need to be fast. Key-value pairs that need ordering but also reasonably fast updates, inserts, and lookups I tend to reach for a gb_tree.

Also, you can implement a custom sort function and run your map through as seen in this thread Enum.sort_by to sort a record set (i.e. a list of maps) based on 2 "columns" - #2 by benwilson512

gregvaughn

gregvaughn

Historical trivia: back before maps were introduced into Erlang, Elixir had a module named ListDict which managed the data structure you describe – an ordered list of two element tuples that could be treated like a map.

rvirding

rvirding

Creator of Erlang

To make matters worse (? :grinning:) the ordering of elements in maps is completely undefined and changes depending on the number of elements. It use to be that for less than 32 elements the ordering was term ordering and for more elements it was “random” depending on the internal search algorithm used.

The thing to remember is that the actual ordering is purely internal. There are iterator functions which can give you some control of which order you want to step over the elements.

binarytemple

binarytemple

Convert to a list of tuples, then sort using a comparator function

map
  |> Map.to_list()
  |>  |> Enum.sort_by(fn {key, _value} -> key end)

Where Next? Top

Trending in Questions Top

RSP87
I’m working on a project that simulates the bumbl example in the programming phoenix book. It acts almost like an email client. We have a...
New
nseaSeb
Hello, I know there is an approach for handling lists that allows for optimized traversal, but I can’t recall the specific method (somet...
New
RemyXRenard
I’m seeing that a list inside a Kino.DataTable will be interpreted as a charlist, even if the Kino.configure() is set to charlists: :as_l...
New
velrest
So my question is quite simple and i have found no conclusive answer on forum, google or AI. Should we use :erlang.float for Integer to ...
New
brecabral
Documentation While reading the Scoped Routes section, I noticed that the documentation currently refers to a problem without explainin...
New
samoloth
Hi, I’ve just set up an application with ash_authentication. There is only magic link strategy for now, so there is no confirmation add o...
New
FlyingNoodle
If a change or preparation module uses Ash.Changeset.get_argument/2 or Ash.Query.get_argument/2 (or any of the other get_argument functio...
New

Other Trending Topics Top

mudasobwa
I am happy to introduce the very α version of the new programming language compiled to BEAM. Welcome Cure. It has literally three kille...
New
marciok
Hi there! We created Gust: A task orchestrator inspired by Airflow. For those who have never heard about Aiflow, it’s a Python-based wor...
New
jimsynz
Beam Bots (or just BB for short) is a framework for building fault-tolerant robotics applications in Elixir using familiar OTP patterns. ...
New
Dmk
Xamal is a deployment tool for Elixir apps that deploys native releases to bare metal servers over SSH. It’s a port of GitHub - basecamp/...
New
netoum
Corex is an accessible, unstyled UI component library for Phoenix that integrates Zag.js state machines using Vanilla JavaScript and Live...
New
webofbits
With AI doing more of the implementation work, I’ve been wondering how much coding I should deliberately keep doing myself. My main conc...
#ai
New

We're in Beta

About us Mission Statement

Options

Thread Display Mode




Thread Preview

Skip Thread Previews