# Sort rows in a dataframe based on a predefined order

**URL:** <https://discourse.julialang.org/t/sort-rows-in-a-dataframe-based-on-a-predefined-order/68272>\
**Category:** New to Julia\
**Tags:** sort, dataframes\
**Created:** [September 16, 2021, 3:48pm UTC](https://discourse.julialang.org/t/sort-rows-in-a-dataframe-based-on-a-predefined-order/68272 "2021-09-16T15:48:44Z")\
**Posts on this page:** 6\
**Page:** 1

<div class="post-metadata">

**Author:** ![Xiao](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/xiao/32/29220_2.png) [@Xiao](https://discourse.julialang.org/u/Xiao)\
**Post date:** [September 16, 2021, 3:48pm UTC](https://discourse.julialang.org/t/sort-rows-in-a-dataframe-based-on-a-predefined-order/68272/1 "2021-09-16T15:48:44Z")

</div>

New to Julia, and have taken (much) effort in seeking a solution to the ‘simple’ question but failed.

```julia
julia> df = DataFrame(col1= ['a', 'b', 'c'], col2 = [1,2,3])
3×2 DataFrame
 Row │ col1 col2  
     │ Char Int64 
─────┼─────────────
   1 │ a 1
   2 │ b 2
   3 │ c 3

julia> order1 = ["b", "a", "c"]
3-element Vector{String}:
 "b"
 "a"
 "c"

```

Please help on how to sort the ‘df’ to follow the ‘order1’.  
THANK YOU!

---

<div class="post-metadata">

**Author:** ![pdeffebach](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/pdeffebach/32/10320_2.png) [@pdeffebach](https://discourse.julialang.org/u/pdeffebach)\
**Post date:** [September 16, 2021, 3:55pm UTC](https://discourse.julialang.org/t/sort-rows-in-a-dataframe-based-on-a-predefined-order/68272/2 "2021-09-16T15:55:24Z")

</div>

One thing to note, in Julia, unlike python and R, `'a'` is not the same as `"a"`. The first is a character, the second is a string.

This is actually kind of hard. I can’t think of a good solution using DataFrames.jl’s `sort` function. So instead here is a solution using DataFramesMeta.jl.

```julia
julia> df = DataFrame(col1= ["a", "b", "c"], col2 = [1,2,3]);

julia> order1 = ["b", "a", "c"];

julia> using DataFramesMeta

julia> @rorderby df findfirst(==(:col1), order1)
3×2 DataFrame
 Row │ col1 col2  
     │ String Int64 
─────┼───────────────
   1 │ b 2
   2 │ a 1
   3 │ c 3

```

I hope someone things of something better!

---

<div class="post-metadata">

**Author:** ![Nathan\_Boyer](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/nathan_boyer/32/14825_2.png) [@Nathan\_Boyer](https://discourse.julialang.org/u/Nathan_Boyer)\
**Post date:** [September 16, 2021, 5:38pm UTC](https://discourse.julialang.org/t/sort-rows-in-a-dataframe-based-on-a-predefined-order/68272/3 "2021-09-16T17:38:08Z")

</div>

Alternative without `DataFramesMeta` package:

```julia
julia> df.order=[findfirst(df.col1.==x) for x in order1]
3-element Vector{Int64}:
 2
 1
 3

julia> sort!(df, :order)
3×3 DataFrame
 Row │ col1 col2 order 
     │ Char Int64 Int64 
─────┼────────────────────
   1 │ b 2 1
   2 │ a 1 2
   3 │ c 3 3

julia> select!(df, Not(:order))
3×2 DataFrame
 Row │ col1 col2  
     │ Char Int64 
─────┼─────────────
   1 │ b 2
   2 │ a 1
   3 │ c 3

```

---

<div class="post-metadata">

**Author:** ![rafael.guerra](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/rafael.guerra/32/216610_2.png) [@rafael.guerra](https://discourse.julialang.org/u/rafael.guerra)\
**Post date:** [September 16, 2021, 11:33pm UTC](https://discourse.julialang.org/t/sort-rows-in-a-dataframe-based-on-a-predefined-order/68272/4 "2021-09-16T23:33:36Z")

</div>

You could also consider (_initial post had the arguments order swapped, corrected now_):

```julia
df[indexin(order1, df.col1),:]

```

result:

```julia
3×2 DataFrame
 Row │ col1 col2  
     │ String Int64 
─────┼───────────────
   1 │ b 2
   2 │ a 1
   3 │ c 3

```

---

<div class="post-metadata">

**Author:** ![Xiao](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/xiao/32/29220_2.png) [@Xiao](https://discourse.julialang.org/u/Xiao)\
**Post date:** [September 17, 2021, 1:22am UTC](https://discourse.julialang.org/t/sort-rows-in-a-dataframe-based-on-a-predefined-order/68272/5 "2021-09-17T01:22:09Z")

</div>

Thanks Rafael,  
Your code works on this example! But it doesn’t for the dataframe below:

```julia
julia> df2
5×2 DataFrame
 Row │ sample reads    
     │ String Int64    
─────┼─────────────────────────
   1 │ RD58-100pg_S7 6096257
   2 │ RD58-10ng_S10 12590390
   3 │ RD58-10pg_S6 2216467
   4 │ RD58-1ng_S9 5381029
   5 │ RD58-500pg_S8 6870582

julia> myOrder = ["RD58-10pg_S6", "RD58-100pg_S7", "RD58-500pg_S8", "RD58-1ng_S9", "RD58-10ng_S10"]
5-element Vector{String}:
 "RD58-10pg_S6"
 "RD58-100pg_S7"
 "RD58-500pg_S8"
 "RD58-1ng_S9"
 "RD58-10ng_S10"

julia> df2[indexin(df2.sample, myOrder),:]
5×2 DataFrame
 Row │ sample reads    
     │ String Int64    
─────┼─────────────────────────
   1 │ RD58-10ng_S10 12590390
   2 │ RD58-500pg_S8 6870582
   3 │ RD58-100pg_S7 6096257
   4 │ RD58-1ng_S9 5381029
   5 │ RD58-10pg_S6 2216467

```

@pdeffebach’s code works well.

```julia
julia> @rorderby df2 findfirst(==(:sample), myOrder)
5×2 DataFrame
 Row │ sample reads    
     │ String Int64    
─────┼─────────────────────────
   1 │ RD58-10pg_S6 2216467
   2 │ RD58-100pg_S7 6096257
   3 │ RD58-500pg_S8 6870582
   4 │ RD58-1ng_S9 5381029
   5 │ RD58-10ng_S10 12590390

```

Thanks!

---

<div class="post-metadata">

**Author:** ![rafael.guerra](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/rafael.guerra/32/216610_2.png) [@rafael.guerra](https://discourse.julialang.org/u/rafael.guerra)\
**Post date:** [September 17, 2021, 6:14am UTC](https://discourse.julialang.org/t/sort-rows-in-a-dataframe-based-on-a-predefined-order/68272/6 "2021-09-17T06:14:03Z")

</div>

Sorry, the order of the arguments needs to be swapped (_corrected order in post above_).

For your last example:

```julia
using DataFrames
col1 = ["RD58-100pg_S7", "RD58-10ng_S10", "RD58-10pg_S6", "RD58-1ng_S9", "RD58-500pg_S8"]
col2 = [6096257, 12590390, 2216467, 5381029,6870582]
df = DataFrame(col1=col1, col2=col2)
order1 = ["RD58-10pg_S6", "RD58-100pg_S7", "RD58-500pg_S8", "RD58-1ng_S9", "RD58-10ng_S10"]

```

Herein the result:

```julia
df[indexin(order1, df.col1),:]

5×2 DataFrame
 Row │ col1 col2     
     │ String Int64    
─────┼─────────────────────────
   1 │ RD58-10pg_S6 2216467
   2 │ RD58-100pg_S7 6096257
   3 │ RD58-500pg_S8 6870582
   4 │ RD58-1ng_S9 5381029
   5 │ RD58-10ng_S10 12590390

```
