# Sorting by two values (basic sorting)

**URL:** https://discourse.julialang.org/t/sorting-by-two-values-basic-sorting/56961
**Category:** New to Julia
**Tags:** sort, arrays
**Created:** [March 11, 2021, 5:46pm UTC](https://discourse.julialang.org/t/sorting-by-two-values-basic-sorting/56961 "2021-03-11T17:46:43Z")
**Posts on this page:** 8
**Page:** 1

<div class="post-metadata">

### Author: ![lmiq](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/lmiq/32/18314_2.png) [@lmiq](https://discourse.julialang.org/u/lmiq)
#### Post date: [March 11, 2021, 5:46pm UTC](https://discourse.julialang.org/t/sorting-by-two-values-basic-sorting/56961/1 "2021-03-11T17:46:43Z")

</div>

This is probably fairly simple. I want to sort a set of tuples first by the second value, and then by the first value, like this:

```julia
julia> a = [rand(1:3,2) for i in 1: 5]
5-element Array{Array{Int64,1},1}:
 [2, 1]
 [3, 2]
 [3, 2]
 [1, 1]
 [2, 1]

julia> sort!(a, by = x -> x[2])
5-element Array{Array{Int64,1},1}:
 [2, 1]
 [1, 1]
 [2, 1]
 [3, 2]
 [3, 2]

julia> sort!(a, by = x -> x[1])
5-element Array{Array{Int64,1},1}:
 [1, 1]
 [2, 1]
 [2, 1]
 [3, 2]
 [3, 2]

```

The result is perfectly fine. However, I am somewhat unsure if the result of the second sorting might be dependent on the sorting algorithm used. Am I safe with that?

In this case I really don’t care about performance, but I wonder if there is a special function or syntax for this kind of thing.

---

<div class="post-metadata">

### Author: ![Jeff\_Emanuel](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/jeff_emanuel/32/15440_2.png) [@Jeff\_Emanuel](https://discourse.julialang.org/u/Jeff_Emanuel)
#### Post date: [March 11, 2021, 5:53pm UTC](https://discourse.julialang.org/t/sorting-by-two-values-basic-sorting/56961/2 "2021-03-11T17:53:22Z")

</div>

It is dependent on the algorithm, but the default Julia sort algorithm is stable, which means that equal keys will be in the same order after sort as before. You can supply a function to sort that gives the relative order of two elements. See the `lt` keyword argument.

---

<div class="post-metadata">

### Author: ![lmiq](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/lmiq/32/18314_2.png) [@lmiq](https://discourse.julialang.org/u/lmiq)
#### Post date: [March 11, 2021, 5:56pm UTC](https://discourse.julialang.org/t/sorting-by-two-values-basic-sorting/56961/3 "2021-03-11T17:56:50Z")

</div>

> [@Jeff\_Emanuel](#):
>
> You can supply a function to sort that gives the relative order of two elements

Yes, of course, that is much smarter.

---

<div class="post-metadata">

### Author: ![jameson](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/jameson/32/23_2.png) [@jameson](https://discourse.julialang.org/u/jameson)
#### Post date: [March 11, 2021, 5:57pm UTC](https://discourse.julialang.org/t/sorting-by-two-values-basic-sorting/56961/4 "2021-03-11T17:57:38Z")

</div>

> [@lmiq](#):
>
> ```julia
> julia> sort!(a, by = x -> x[1])
> 
> ```

Those aren’t tuples, they’re vectors, and they already sort lexicographically. Thus, we can generically have `by` return the list of keys in order to compare:

```julia
julia> sort!(a, by=x -> (x[1], x[2]))

```

Which in this case is also just:

```julia
julia> sort!(a, by=identity)

```

or just

```julia
julia> sort!(a)

```

---

<div class="post-metadata">

### Author: ![lmiq](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/lmiq/32/18314_2.png) [@lmiq](https://discourse.julialang.org/u/lmiq)
#### Post date: [March 11, 2021, 6:00pm UTC](https://discourse.julialang.org/t/sorting-by-two-values-basic-sorting/56961/5 "2021-03-11T18:00:45Z")

</div>

> [@jameson](#):
>
> Those aren’t tuples, they’re vectors

Yes, sorry, in the MWE I have used vectors, but my real case is with tuples. Good to know that, anyway.

---

<div class="post-metadata">

### Author: ![greg\_plowman](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/greg_plowman/32/8100_2.png) [@greg\_plowman](https://discourse.julialang.org/u/greg_plowman)
#### Post date: [March 11, 2021, 8:20pm UTC](https://discourse.julialang.org/t/sorting-by-two-values-basic-sorting/56961/6 "2021-03-11T20:20:05Z")

</div>

> [@jameson](#):
>
> Thus, we can generically have `by` return the list of keys in order to compare:
> 
> ```julia
> julia> sort!(a, by=x -> (x[1], x[2]))
> 
> ```
> 
> Which in this case is also just:
> 
> ```julia
> julia> sort!(a, by=identity)
> 
> ```
> 
> or just
> 
> ```julia
> julia> sort!(a)
> 
> ```

Yes, but in this case, OP wants:

```julia
sort!(a, by = x -> (x[2], x[1]))

```

---

<div class="post-metadata">

### Author: ![lmiq](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/lmiq/32/18314_2.png) [@lmiq](https://discourse.julialang.org/u/lmiq)
#### Post date: [March 11, 2021, 8:56pm UTC](https://discourse.julialang.org/t/sorting-by-two-values-basic-sorting/56961/7 "2021-03-11T20:56:29Z")

</div>

Actually there is a `isless` function defined for tuples that does what I want, it seems:

```julia
julia> a = [(rand(1:3),rand(1:3)) for i in 1: 5]
5-element Array{Tuple{Int64,Int64},1}:
 (1, 3)
 (1, 3)
 (1, 2)
 (3, 3)
 (2, 1)

julia> sort!(a)
5-element Array{Tuple{Int64,Int64},1}:
 (1, 2)
 (1, 3)
 (1, 3)
 (2, 1)
 (3, 3)

```

(I had to define a custom one because in my case the tuple was something computed from a struct, but that is another story).

---

<div class="post-metadata">

### Author: ![greg\_plowman](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/greg_plowman/32/8100_2.png) [@greg\_plowman](https://discourse.julialang.org/u/greg_plowman)
#### Post date: [March 11, 2021, 9:21pm UTC](https://discourse.julialang.org/t/sorting-by-two-values-basic-sorting/56961/8 "2021-03-11T21:21:59Z")

</div>

> [@lmiq](#):
>
> Actually there is a `isless` function defined for tuples that does what I want, it seems:

Yes, that’s what `sort!(a, by = x -> (x[2], x[1]))` uses
