• Introduction
  • Getting Started
    • Resources
  • Variables
    • Allowed Variable Names
    • Stylistic Conventions
  • Integers and Floating-Point Numbers
    • Integers
    • Floating-Point Numbers
    • Arbitrary Precision Arithmetic
    • Numeric Literal Coefficients
    • Literal zero and one
  • Mathematical Operations and Elementary Functions
    • Arithmetic Operators
    • Bitwise Operators
    • Updating operators
    • Numeric Comparisons
    • Numerical Conversions
  • Complex and Rational Numbers
    • Complex Numbers
    • Rational Numbers
  • Strings
    • Characters
    • String Basics
    • Unicode and UTF-8
    • Interpolation
    • Triple-Quoted String Literals
    • Common Operations
    • Non-Standard String Literals
    • Regular Expressions
    • Byte Array Literals
    • Version Number Literals
  • Functions
    • Argument Passing Behavior
    • The return Keyword
    • Operators Are Functions
    • Operators With Special Names
    • Anonymous Functions
    • Multiple Return Values
    • Varargs Functions
    • Optional Arguments
    • Keyword Arguments
    • Evaluation Scope of Default Values
    • Do-Block Syntax for Function Arguments
    • Dot Syntax for Vectorizing Functions
    • Further Reading
  • Control Flow
    • Compound Expressions
    • Conditional Evaluation
    • Short-Circuit Evaluation
    • Repeated Evaluation: Loops
    • Exception Handling
    • Tasks (aka Coroutines)
  • Scope of Variables
    • Global Scope
    • Local Scope
    • Constants
  • Types
    • Type Declarations
    • Abstract Types
    • Bits Types
    • Composite Types
    • Immutable Composite Types
    • Declared Types
    • Type Unions
    • Parametric Types
    • Type Aliases
    • Operations on Types
    • “Value types”
    • Nullable Types: Representing Missing Values
  • Methods
    • Defining Methods
    • Method Ambiguities
    • Parametric Methods
    • Parametrically-constrained Varargs methods
    • Note on Optional and keyword Arguments
    • Function-like objects
    • Empty generic functions
  • Constructors
    • Outer Constructor Methods
    • Inner Constructor Methods
    • Incomplete Initialization
    • Parametric Constructors
    • Case Study: Rational
    • Constructors and Conversion
    • Outer-only constructors
  • Conversion and Promotion
    • Conversion
    • Promotion
  • Interfaces
    • Iteration
    • Indexing
    • Abstract Arrays
  • Modules
    • Summary of module usage
  • Documentation
    • Accessing Documentation
    • Functions & Methods
    • Advanced Usage
    • Syntax Guide
    • Markdown syntax
    • Markdown Syntax Extensions
  • Metaprogramming
    • Program representation
    • Expressions and evaluation
    • Macros
    • Code Generation
    • Non-Standard String Literals
    • Generated functions
  • Multi-dimensional Arrays
    • Arrays
    • Sparse Matrices
  • Linear algebra
    • Matrix factorizations
    • Special matrices
  • Networking and Streams
    • Basic Stream I/O
    • Text I/O
    • IO Output Contextual Properties
    • Working with Files
    • A simple TCP example
    • Resolving IP Addresses
  • Parallel Computing
    • Code Availability and Loading Packages
    • Data Movement
    • Parallel Map and Loops
    • Synchronization With Remote References
    • Scheduling
    • Channels
    • Remote references and AbstractChannels
    • Remote References and Distributed Garbage Collection
    • Shared Arrays
    • Shared Arrays and Distributed Garbage Collection
    • ClusterManagers
    • Cluster Managers with custom transports
    • Network requirements for LocalManager and SSHManager
    • Cluster cookie
    • Specifying network topology (Experimental)
    • Multi-threading (Experimental)
    • @threadcall (Experimental)
  • Date and DateTime
    • Constructors
    • Durations/Comparisons
    • Accessor Functions
    • Query Functions
    • TimeType-Period Arithmetic
    • Adjuster Functions
    • Period Types
    • Rounding
  • Running External Programs
    • Interpolation
    • Quoting
    • Pipelines
  • Calling C and Fortran Code
    • Creating C-Compatible Julia Function Pointers
    • Mapping C Types to Julia
    • Mapping C Functions to Julia
    • Some Examples of C Wrappers
    • Garbage Collection Safety
    • Non-constant Function Specifications
    • Indirect Calls
    • Calling Convention
    • Accessing Global Variables
    • Accessing Data through a Pointer
    • Thread-safety
    • More About Callbacks
    • C++
  • Handling Operating System Variation
  • Interacting With Julia
    • The different prompt modes
    • Key bindings
    • Tab completion
    • Customizing Colors
  • Embedding Julia
    • High-Level Embedding
    • Converting Types
    • Calling Julia Functions
    • Memory Management
    • Working with Arrays
    • Exceptions
  • Packages
    • Package Status
    • Adding and Removing Packages
    • Offline Installation of Packages
    • Installing Unregistered Packages
    • Updating Packages
    • Checkout, Pin and Free
    • Custom METADATA Repository
  • Package Development
    • Initial Setup
    • Making changes to an existing package
    • Creating a new Package
    • Fixing Package Requirements
    • Requirements Specification
  • Profiling
    • Basic usage
    • Accumulation and clearing
    • Options for controlling the display of profile results
    • Configuration
  • Memory allocation analysis
  • Stack Traces
    • Viewing a stack trace
    • Extracting useful information
    • Error handling
    • Comparison with backtrace()
  • Performance Tips
    • Avoid global variables
    • Measure performance with @time and pay attention to memory allocation
    • Tools
    • Avoid containers with abstract type parameters
    • Type declarations
    • Break functions into multiple definitions
    • Write “type-stable” functions
    • Avoid changing the type of a variable
    • Separate kernel functions (aka, function barriers)
    • Types with values-as-parameters
    • The dangers of abusing multiple dispatch (aka, more on types with values-as-parameters)
    • Access arrays in memory order, along columns
    • Pre-allocating outputs
    • Avoid string interpolation for I/O
    • Optimize network I/O during parallel execution
    • Fix deprecation warnings
    • Tweaks
    • Performance Annotations
    • Treat Subnormal Numbers as Zeros
    • @code_warntype
  • Workflow Tips
    • REPL-based workflow
    • Browser-based workflow
  • Style Guide
    • Write functions, not just scripts
    • Avoid writing overly-specific types
    • Handle excess argument diversity in the caller
    • Append ! to names of functions that modify their arguments
    • Avoid strange type Unions
    • Avoid type Unions in fields
    • Avoid elaborate container types
    • Use naming conventions consistent with Julia’s base/
    • Don’t overuse try-catch
    • Don’t parenthesize conditions
    • Don’t overuse ...
    • Don’t use unnecessary static parameters
    • Avoid confusion about whether something is an instance or a type
    • Don’t overuse macros
    • Don’t expose unsafe operations at the interface level
    • Don’t overload methods of base container types
    • Be careful with type equality
    • Do not write x->f(x)
    • Avoid using floats for numeric literals in generic code when possible
  • Frequently Asked Questions
    • Sessions and the REPL
    • Functions
    • Types, type declarations, and constructors
    • Packages and Modules
    • Nothingness and missing values
    • Memory
    • Asynchronous IO and concurrent synchronous writes
    • Julia Releases
  • Noteworthy Differences from other Languages
    • Noteworthy differences from MATLAB
    • Noteworthy differences from R
    • Noteworthy differences from Python
    • Noteworthy differences from C/C++
  • Unicode Input
  • Essentials
    • Introduction
    • Getting Around
    • All Objects
    • Types
    • Generic Functions
    • Syntax
    • Nullables
    • System
    • Errors
    • Events
    • Reflection
    • Internals
  • Collections and Data Structures
    • Iteration
    • General Collections
    • Iterable Collections
    • Indexable Collections
    • Associative Collections
    • Set-Like Collections
    • Dequeues
    • PriorityQueue
    • Heap Functions
  • Mathematics
    • Mathematical Operators
    • Mathematical Functions
    • Statistics
    • Signal Processing
    • Numerical Integration
  • Numbers
    • Standard Numeric Types
    • Data Formats
    • General Number Functions and Constants
    • BigFloats
    • Random Numbers
  • Strings
  • Arrays
    • Basic functions
    • Constructors
    • Mathematical operators and functions
    • Indexing, Assignment, and Concatenation
    • Array functions
    • Combinatorics
    • BitArrays
    • Sparse Vectors and Matrices
  • Tasks and Parallel Computing
    • Tasks
    • General Parallel Computing Support
    • Shared Arrays
    • Multi-Threading
    • ccall using a threadpool (Experimental)
    • Synchronization Primitives
    • Cluster Manager Interface
  • Linear Algebra
    • Standard Functions
    • Low-level matrix operations
    • BLAS Functions
    • LAPACK Functions
  • Constants
  • Filesystem
  • I/O and Network
    • General I/O
    • Text I/O
    • Multimedia I/O
    • Memory-mapped I/O
    • Network I/O
  • Punctuation
  • Sorting and Related Functions
    • Sorting Functions
    • Order-Related Functions
    • Sorting Algorithms
  • Package Manager Functions
  • Dates and Time
    • Dates and Time Types
    • Dates Functions
  • Unit Testing
    • Testing Base Julia
    • Basic Unit Tests
    • Working with Test Sets
    • Other Test Macros
    • Broken Tests
    • Creating Custom AbstractTestSet Types
  • C Interface
  • LLVM Interface
  • C Standard Library
  • Dynamic Linker
  • Profiling
  • StackTraces
  • SIMD Support
  • Reflection and introspection
  • Documentation of Julia’s Internals
    • Initialization of the Julia runtime
    • Eval of Julia code
    • Julia ASTs
    • More about types
    • Memory layout of Julia Objects
    • Julia Functions
    • Calling Conventions
    • Base.Cartesian
    • Talking to the compiler (the :meta mechanism)
    • SubArrays
    • System Image Building
    • Working with LLVM
    • printf() and stdio in the Julia runtime
    • Bounds checking
    • Proper maintenance and care of multi-threading locks
    • Arrays with custom indices
  • Developing/debugging Julia’s C code
    • Reporting and analyzing crashes (segfaults)
    • gdb debugging tips
    • Using Valgrind with Julia
    • Sanitizer support
 
Julia Language
  • Docs »
  • Sorting and Related Functions
  • View page source

Sorting and Related Functions¶

Julia has an extensive, flexible API for sorting and interacting with already-sorted arrays of values. By default, Julia picks reasonable algorithms and sorts in standard ascending order:

julia>sort([2,3,1])3-elementArray{Int64,1}:123

You can easily sort in reverse order as well:

julia>sort([2,3,1],rev=true)3-elementArray{Int64,1}:321

To sort an array in-place, use the “bang” version of the sort function:

julia>a=[2,3,1];julia>sort!(a);julia>a3-elementArray{Int64,1}:123

Instead of directly sorting an array, you can compute a permutation of the array’s indices that puts the array into sorted order:

julia>v=randn(5)5-elementArray{Float64,1}:0.2972880.382396-0.597634-0.0104452-0.839027julia>p=sortperm(v)5-elementArray{Int64,1}:53412julia>v[p]5-elementArray{Float64,1}:-0.839027-0.597634-0.01044520.2972880.382396

Arrays can easily be sorted according to an arbitrary transformation of their values:

julia>sort(v,by=abs)5-elementArray{Float64,1}:-0.01044520.2972880.382396-0.597634-0.839027

Or in reverse order by a transformation:

julia>sort(v,by=abs,rev=true)5-elementArray{Float64,1}:-0.839027-0.5976340.3823960.297288-0.0104452

If needed, the sorting algorithm can be chosen:

julia>sort(v,alg=InsertionSort)5-elementArray{Float64,1}:-0.839027-0.597634-0.01044520.2972880.382396

All the sorting and order related functions rely on a “less than” relation defining a total order on the values to be manipulated. The isless function is invoked by default, but the relation can be specified via the lt keyword.

Sorting Functions¶

sort!(v, [alg=<algorithm>,] [by=<transform>,] [lt=<comparison>,] [rev=false])¶

Sort the vector v in place. QuickSort is used by default for numeric arrays while MergeSort is used for other arrays. You can specify an algorithm to use via the alg keyword (see Sorting Algorithms for available algorithms). The by keyword lets you provide a function that will be applied to each element before comparison; the lt keyword allows providing a custom “less than” function; use rev=true to reverse the sorting order. These options are independent and can be used together in all possible combinations: if both by and lt are specified, the lt function is applied to the result of the by function; rev=true reverses whatever ordering specified via the by and lt keywords.

sort(v, [alg=<algorithm>,] [by=<transform>,] [lt=<comparison>,] [rev=false])¶

Variant of sort! that returns a sorted copy of v leaving v itself unmodified.

sort(A, dim, [alg=<algorithm>,] [by=<transform>,] [lt=<comparison>,] [rev=false])

Sort a multidimensional array A along the given dimension.

sortperm(v, [alg=<algorithm>,] [by=<transform>,] [lt=<comparison>,] [rev=false])¶

Return a permutation vector of indices of v that puts it in sorted order. Specify alg to choose a particular sorting algorithm (see Sorting Algorithms). MergeSort is used by default, and since it is stable, the resulting permutation will be the lexicographically first one that puts the input array into sorted order – i.e. indices of equal elements appear in ascending order. If you choose a non-stable sorting algorithm such as QuickSort, a different permutation that puts the array into order may be returned. The order is specified using the same keywords as sort!.

See also sortperm!().

sortperm!(ix, v, [alg=<algorithm>,] [by=<transform>,] [lt=<comparison>,] [rev=false,] [initialized=false])¶

Like sortperm, but accepts a preallocated index vector ix. If initialized is false (the default), ix is initialized to contain the values 1:length(v).

See also sortperm().

sortrows(A, [alg=<algorithm>,] [by=<transform>,] [lt=<comparison>,] [rev=false])¶

Sort the rows of matrix A lexicographically.

sortcols(A, [alg=<algorithm>,] [by=<transform>,] [lt=<comparison>,] [rev=false])¶

Sort the columns of matrix A lexicographically.

Order-Related Functions¶

issorted(v, [by=<transform>,] [lt=<comparison>,] [rev=false])¶

Test whether a vector is in sorted order. The by, lt and rev keywords modify what order is considered to be sorted just as they do for sort.

searchsorted(a, x, [by=<transform>,] [lt=<comparison>,] [rev=false])¶

Returns the range of indices of a which compare as equal to x according to the order specified by the by, lt and rev keywords, assuming that a is already sorted in that order. Returns an empty range located at the insertion point if a does not contain values equal to x.

searchsortedfirst(a, x, [by=<transform>,] [lt=<comparison>,] [rev=false])¶

Returns the index of the first value in a greater than or equal to x, according to the specified order. Returns length(a)+1 if x is greater than all values in a.

searchsortedlast(a, x, [by=<transform>,] [lt=<comparison>,] [rev=false])¶

Returns the index of the last value in a less than or equal to x, according to the specified order. Returns 0 if x is less than all values in a.

select!(v, k, [by=<transform>,] [lt=<comparison>,] [rev=false])¶

Partially sort the vector v in place, according to the order specified by by, lt and rev so that the value at index k (or range of adjacent values if k is a range) occurs at the position where it would appear if the array were fully sorted via a non-stable algorithm. If k is a single index, that value is returned; if k is a range, an array of values at those indices is returned. Note that select! does not fully sort the input array.

select(v, k, [by=<transform>,] [lt=<comparison>,] [rev=false])¶

Variant of select! which copies v before partially sorting it, thereby returning the same thing as select! but leaving v unmodified.

selectperm(v, k, [alg=<algorithm>,] [by=<transform>,] [lt=<comparison>,] [rev=false])¶

Return a partial permutation of the vector v, according to the order specified by by, lt and rev, so that v[output] returns the first k (or range of adjacent values if k is a range) values of a fully sorted version of v. If k is a single index (Integer), an array of the first k indices is returned; if k is a range, an array of those indices is returned. Note that the handling of integer values for k is different from select in that it returns a vector of k elements instead of just the k th element. Also note that this is equivalent to, but more efficient than, calling sortperm(...)[k]

selectperm!(ix, v, k, [alg=<algorithm>,] [by=<transform>,] [lt=<comparison>,] [rev=false,] [initialized=false])¶

Like selectperm, but accepts a preallocated index vector ix. If initialized is false (the default), ix is initialized to contain the values 1:length(ix).

Sorting Algorithms¶

There are currently four sorting algorithms available in base Julia:

  • InsertionSort
  • QuickSort
  • PartialQuickSort(k)
  • MergeSort

InsertionSort is an O(n^2) stable sorting algorithm. It is efficient for very small n, and is used internally by QuickSort.

QuickSort is an O(n log n) sorting algorithm which is in-place, very fast, but not stable – i.e. elements which are considered equal will not remain in the same order in which they originally appeared in the array to be sorted. QuickSort is the default algorithm for numeric values, including integers and floats.

PartialQuickSort(k) is similar to QuickSort, but the output array is only sorted up to index k if k is an integer, or in the range of k if k is an OrdinalRange. For example:

x=rand(1:500,100)k=50k2=50:100s=sort(x;alg=QuickSort)ps=sort(x;alg=PartialQuickSort(k))qs=sort(x;alg=PartialQuickSort(k2))map(issorted,(s,ps,qs))# => (true, false, false)map(x->issorted(x[1:k]),(s,ps,qs))# => (true, true, false)map(x->issorted(x[k2]),(s,ps,qs))# => (true, false, true)s[1:k]==ps[1:k]# => trues[k2]==qs[k2]# => true

MergeSort is an O(n log n) stable sorting algorithm but is not in-place – it requires a temporary array of half the size of the input array – and is typically not quite as fast as QuickSort. It is the default algorithm for non-numeric data.

The default sorting algorithms are chosen on the basis that they are fast and stable, or appear to be so. For numeric types indeed, QuickSort is selected as it is faster and indistinguishable in this case from a stable sort (unless the array records its mutations in some way). The stability property comes at a non-negligible cost, so if you don’t need it, you may want to explicitly specify your preferred algorithm, e.g. sort!(v,alg=QuickSort).

The mechanism by which Julia picks default sorting algorithms is implemented via the Base.Sort.defalg function. It allows a particular algorithm to be registered as the default in all sorting functions for specific arrays. For example, here are the two default methods from sort.jl:

defalg(v::AbstractArray)=MergeSortdefalg{T<:Number}(v::AbstractArray{T})=QuickSort

As for numeric arrays, choosing a non-stable default algorithm for array types for which the notion of a stable sort is meaningless (i.e. when two values comparing equal can not be distinguished) may make sense.

Next Previous

Sphinx theme provided by Read the Docs