Sorting algorithms/Sleep sort: Difference between revisions

From Rosetta Code
Content added Content deleted
(→‎{{header|F#}}: Corrected header as suggested on the Count examples/Full list/Tier 4 talk page)
(Implementation for Visual Basic .NET added)
Line 2,137: Line 2,137:
5
5
9
9
</pre>

=={{header|Visual Basic .NET}}==
<lang vbnet>Imports System.Threading

Module Module1

Sub SleepSort(items As IEnumerable(Of Integer))
For Each item In items
Task.Factory.StartNew(Sub()
Thread.Sleep(1000 * item)
Console.WriteLine(item)
End Sub)
Next
End Sub

Sub Main()
SleepSort({1, 5, 2, 1, 8, 10, 3})
Console.ReadKey()
End Sub

End Module</lang>

{{out}}
<pre>
1
1
2
3
5
8
10
</pre>
</pre>



Revision as of 07:28, 3 August 2022

Task
Sorting algorithms/Sleep sort
You are encouraged to solve this task according to the task description, using any language you may know.

In general, sleep sort works by starting a separate task for each item to be sorted, where each task sleeps for an interval corresponding to the item's sort key, then emits the item. Items are then collected sequentially in time.

Task: Write a program that implements sleep sort. Have it accept non-negative integers on the command line and print the integers in sorted order. If this is not idomatic in your language or environment, input and output may be done differently. Enhancements for optimization, generalization, practicality, robustness, and so on are not required.

Sleep sort was presented anonymously on 4chan and has been discussed on Hacker News.

Ada

<lang Ada>with Ada.Text_IO; with Ada.Command_Line; use Ada.Command_Line; procedure SleepSort is

  task type PrintTask (num : Integer);
  task body PrintTask is begin
     delay Duration (num) / 100.0;
     Ada.Text_IO.Put(num'Img);
  end PrintTask;
  type TaskAcc is access PrintTask;
  TaskList : array (1 .. Argument_Count) of TaskAcc;

begin

  for i in TaskList'Range loop
     TaskList(i) := new PrintTask(Integer'Value(Argument(i)));
  end loop;

end SleepSort;</lang>

Output:
./sleepsort 35 21 11 1 2 27 32 7 42 20 50 42 25 41 43 14 46 20 30 8
 1 2 7 8 11 14 20 20 21 25 27 30 32 35 41 42 42 43 46 50

APL

<lang APL> sleepsort←{{r}⎕TSYNC{r,←⊃⍵,⎕DL ⍵}&¨⍵,r←⍬} </lang>

AutoHotkey

<lang AutoHotkey>items := [1,5,4,9,3,4] for i, v in SleepSort(items)

   result .= v ", "

MsgBox, 262144, , % result := "[" Trim(result, ", ") "]" return

SleepSort(items){

   global Sorted := []
   slp := 50
   for i, v in items{
       fn := Func("PushFn").Bind(v)
       SetTimer, %fn%, % v * -slp
   }
   Sleep % Max(items*) * slp
   return Sorted

}

PushFn(v){

   global Sorted
   Sorted.Push(v)

}</lang>

Output:
[1, 3, 4, 4, 5, 9]

Bash

<lang bash> function sleep_and_echo {

 sleep "$1"
 echo "$1"

}

for val in "$@"; do

 sleep_and_echo "$val" &

done

wait </lang>

Output:
$ ./sleep_sort.sh 35 21 11 1 2 27 32 7 42 20 50 42 25 41 43 14 46 20 30 8
1
2
7
8
11
14
20
20
21
25
27
30
32
35
41
42
42
43
46
50

BBC BASIC

This does not explicitly 'sleep', but uses timers to implement the different delays. <lang bbcbasic> INSTALL @lib$+"TIMERLIB"

     DIM test%(9)
     test%() = 4, 65, 2, 31, 0, 99, 2, 83, 782, 1
     
     FOR i% = 0 TO DIM(test%(),1)
       p% = EVAL("!^PROCtask" + STR$(i%))
       tid% = FN_ontimer(100 + test%(i%), p%, 0)
     NEXT
     
     REPEAT
       WAIT 0
     UNTIL FALSE
     
     DEF PROCtask0 : PRINT test%(0) : ENDPROC
     DEF PROCtask1 : PRINT test%(1) : ENDPROC
     DEF PROCtask2 : PRINT test%(2) : ENDPROC
     DEF PROCtask3 : PRINT test%(3) : ENDPROC
     DEF PROCtask4 : PRINT test%(4) : ENDPROC
     DEF PROCtask5 : PRINT test%(5) : ENDPROC
     DEF PROCtask6 : PRINT test%(6) : ENDPROC
     DEF PROCtask7 : PRINT test%(7) : ENDPROC
     DEF PROCtask8 : PRINT test%(8) : ENDPROC
     DEF PROCtask9 : PRINT test%(9) : ENDPROC</lang>

Output:

         0
         1
         2
         2
         4
        31
        65
        83
        99
       782

Brainf***

<lang C> >>>>>,----------[++++++++ ++[->+>+<<]>+>[-<<+>>]+++ +++++[-<------>]>>+>,----


<<+[->>>>>+<<<<<]>>

]>>>[<<<<[<<<[->>+<<[->+> [-]<<]]>[-<+>]>[-<<<.>>>> ->>>>>[>>>>>]<-<<<<[<<<<< ]+<]<<<<]>>>>>[>>>>>]<] </lang> Not exactly 'sleep' sort but it is similar: it inputs an array of digits and in each iteration reduces elements by 1. When an element becomes 0 – it prints the original digit.

Input: 1539\n

Output: 1359

C

<lang C>#include <stdlib.h>

  1. include <unistd.h>
  2. include <sys/types.h>
  3. include <sys/wait.h>

int main(int c, char **v) {

       while (--c > 1 && !fork());
       sleep(c = atoi(v[c]));
       printf("%d\n", c);
       wait(0);
       return 0;

}</lang> Running it:<lang>% ./a.out 5 1 3 2 11 6 4 1 2 3 4 5 6 11</lang> If you worry about time efficiency of this sorting algorithm (ha!), you can make it a 100 times faster by replacing the sleep(... with usleep(10000 * (c = atoi(v[c]))). The smaller the coefficient, the faster it is, but make sure it's not comparable to your kernel clock ticks or the wake up sequence will be wrong.

C#

<lang csharp>using System; using System.Collections.Generic; using System.Linq; using System.Threading;

class Program {

   static void ThreadStart(object item)
   {
       Thread.Sleep(1000 * (int)item);
       Console.WriteLine(item);
   }
   static void SleepSort(IEnumerable<int> items)
   {
       foreach (var item in items)
       {
           new Thread(ThreadStart).Start(item);
       }
   }
   static void Main(string[] arguments)
   {
       SleepSort(arguments.Select(int.Parse));
   }

}</lang>

Using Tasks

<lang csharp>var input = new[] { 1, 9, 2, 1, 3 };

foreach (var n in input) Task.Run(() => { Thread.Sleep(n * 1000); Console.WriteLine(n); }); </lang>

Output, i.e. in LINQPad:

1
1
2
3
9

C++

<lang cpp>

  1. include <chrono>
  2. include <iostream>
  3. include <thread>
  4. include <vector>

int main(int argc, char* argv[]) {

 std::vector<std::thread> threads;
 for (int i = 1; i < argc; ++i) {
   threads.emplace_back([i, &argv]() {
     int arg = std::stoi(argv[i]);
     std::this_thread::sleep_for(std::chrono::seconds(arg));
     std::cout << argv[i] << std::endl;
   });
 }
 for (auto& thread : threads) {
   thread.join();
 }

} </lang>

Output:
./a.out 8 15 14 9 17 20 16 24 6 24 21 23 19 23 19 
6
8
9
14
15
16
17
19
19
20
21
23
23
24
24 

Clojure

Using core.async <lang clojure>(ns sleepsort.core

 (require [clojure.core.async :as async :refer [chan go <! <!! >! timeout]]))

(defn sleep-sort [l]

 (let [c (chan (count l))]
   (doseq [i l]
     (go (<! (timeout (* 1000 i)))
         (>! c i)))
   (<!! (async/into [] (async/take (count l) c)))))</lang>

<lang clojure>(sleep-sort [4 5 3 1 2 7 6])

=> [1 2 3 4 5 6 7]</lang>

CoffeeScript

Works with: node.js

<lang coffeescript> after = (s, f) -> setTimeout f, s*1000

  1. Setting Computer Science back at least a century, maybe more,
  2. this algorithm sorts integers using a highly parallelized algorithm.

sleep_sort = (arr) ->

 for n in arr
   do (n) -> after n, -> console.log n
   

do ->

 input = (parseInt(arg) for arg in process.argv[2...])
 sleep_sort input

</lang> output <lang> > time coffee sleep_sort.coffee 5, 1, 3, 4, 2 1 2 3 4 5

real 0m5.184s user 0m0.147s sys 0m0.024s </lang>

Common Lisp

Works with: SBCL

<lang lisp>(defun sleeprint(n)

   (sleep (/ n 10))
   (format t "~a~%" n))

(loop for arg in (cdr sb-ext:*posix-argv*) doing

     (sb-thread:make-thread (lambda() (sleeprint (parse-integer arg)))))

(loop while (not (null (cdr (sb-thread:list-all-threads)))))</lang>

Output:
$ sbcl --script ss.cl 3 1 4 1 5
1
1
3
4
5

D

<lang d>void main(string[] args) {

   import core.thread, std;
   args.drop(1).map!(a => a.to!uint).parallel.each!((a)
   {
       Thread.sleep(dur!"msecs"(a));
       write(a, " ");
   });

}</lang>

Output:
$ ./sorting_algorithms_sleep_sort 200 20 50 10 80
10 20 50 80 200

Dart

<lang dart> void main() async {

 Future<void> sleepsort(Iterable<int> input) => Future.wait(input
     .map((i) => Future.delayed(Duration(milliseconds: i), () => print(i))));
 await sleepsort([3, 10, 2, 120, 122, 121, 54]);

} </lang>

Output:
2
3
10
54
120
121
122

Delphi

<lang Delphi>program SleepSortDemo;

{$APPTYPE CONSOLE}

uses

 Windows, SysUtils, Classes;

type

 TSleepThread = class(TThread)
 private
   FValue: Integer;
   FLock: PRTLCriticalSection;
 protected
   constructor Create(AValue: Integer; ALock: PRTLCriticalSection);
   procedure Execute; override;
 end;

constructor TSleepThread.Create(AValue: Integer; ALock: PRTLCriticalSection); begin

 FValue:= AValue;
 FLock:= ALock;
 inherited Create(False);

end;

procedure TSleepThread.Execute; begin

 Sleep(1000 * FValue);
 EnterCriticalSection(FLock^);
 Write(FValue:3);
 LeaveCriticalSection(FLock^);

end;

var

 A: array[0..15] of Integer;
 Handles: array[0..15] of THandle;
 Threads: array[0..15] of TThread;
 Lock: TRTLCriticalSection;
 I: Integer;

begin

 for I:= Low(A) to High(A) do
   A[I]:= Random(15);
 for I:= Low(A) to High(A) do
   Write(A[I]:3);
 Writeln;
 InitializeCriticalSection(Lock);
 for I:= Low(A) to High(A) do begin
   Threads[I]:= TSleepThread.Create(A[I], @Lock);
   Handles[I]:= Threads[I].Handle;
 end;
 WaitForMultipleObjects(Length(A), @Handles, True, INFINITE);
 for I:= Low(A) to High(A) do
   Threads[I].Free;
 DeleteCriticalSection(Lock);
 Writeln;
 ReadLn;

end.</lang> Output:

  0  0 12  3  4 10  4  2  5  6  1  7  1 12  0  4
  0  0  0  1  1  2  3  4  4  4  5  6  7 10 12 12

Elena

ELENA 5.0 : <lang elena>import extensions; import system'routines; import extensions'threading; import system'threading;

static sync = new object();

extension op {

   sleepSort()
   {
       self.forEach:(n)
       {
           threadControl.start(
           {
               threadControl.sleep(1000 * n);

               lock(sync)
               {
                   console.printLine(n)
               }
           })
       }
   }

}

public program() {

   program_arguments.skipping:1.selectBy(mssgconst toInt<convertorOp>[1]).toArray().sleepSort();

   console.readChar()

}</lang>

Elixir

Translation of: Erlang

<lang elixir>defmodule Sort do

 def sleep_sort(args) do
   Enum.each(args, fn(arg) -> Process.send_after(self, arg, 5 * arg) end)
   loop(length(args))
 end
 
 defp loop(0), do: :ok
 defp loop(n) do
   receive do
       num -> IO.puts num
              loop(n - 1)
   end
 end

end

Sort.sleep_sort [2, 4, 8, 12, 35, 2, 12, 1]</lang>

Output:
1
2
2
4
8
12
12
35

Emacs Lisp

GNU Emacs supports threads, but it's more straightforward to do this by just using timers. Evaluate in the *scratch* buffer by typing C-M-x on the expression: <lang Lisp>(dolist (i '(3 1 4 1 5 92 65 3 5 89 79 3))

 (run-with-timer (* i 0.001) nil 'message "%d" i))</lang>

The output printed in the *Messages* buffer is:

1 [2 times]
3 [3 times]
4
5 [2 times]
65
79
89
92

Erlang

<lang erlang>#!/usr/bin/env escript %% -*- erlang -*- %%! -smp enable -sname sleepsort

main(Args) ->

   lists:foreach(fun(Arg) ->
                         timer:send_after(5 * list_to_integer(Arg), self(), Arg)
                 end, Args),
   loop(length(Args)).

loop(0) ->

   ok;

loop(N) ->

   receive
       Num ->
           io:format("~s~n", [Num]),
           loop(N - 1)
   end.</lang>
Output:
./sleepsort 2 4 8 12 35 2 12 1
1
2
2
4
8
12
12
35

Euphoria

<lang euphoria>include get.e

integer count

procedure sleeper(integer key)

   ? key
   count -= 1

end procedure

sequence s, val atom task

s = command_line() s = s[3..$] if length(s)=0 then

   puts(1,"Nothing to sort.\n")

else

   count = 0
   for i = 1 to length(s) do
       val = value(s[i])
       if val[1] = GET_SUCCESS then
           task = task_create(routine_id("sleeper"),{val[2]})
           task_schedule(task,{val[2],val[2]}/10)
           count += 1
       end if
   end for
   
   while count do
       task_yield()
   end while

end if</lang>

F#

<lang fsharp> let sleepSort (values: seq<int>) =

   values
   |> Seq.map (fun x -> async {
       do! Async.Sleep x
       Console.WriteLine x
   })
   |> Async.Parallel
   |> Async.Ignore
   |> Async.RunSynchronously

</lang>

Usage: <lang fsharp> sleepSort [10; 33; 80; 32] 10 32 33 80 </lang>

Factor

<lang Factor> USING: threads calendar concurrency.combinators ;

sleep-sort ( seq -- ) [ dup seconds sleep . ] parallel-each ;

</lang>

Usage:

<lang Factor> { 1 9 2 6 3 4 5 8 7 0 } sleep-sort </lang>

Fortran

<lang Fortran> program sleepSort

   use omp_lib
   implicit none
   integer::nArgs,myid,i,stat
   integer,allocatable::intArg(:)
   character(len=5)::arg
   !$omp master
   nArgs=command_argument_count()
   if(nArgs==0)stop ' : No argument is given !'
   allocate(intArg(nArgs))
   do i=1,nArgs
       call get_command_argument(i, arg)

read(arg,'(I5)',iostat=stat)intArg(i) if(intArg(i)<0 .or. stat/=0) stop&

       &' :Only 0 or positive integer allowed !'
   end do
   call omp_set_num_threads(nArgs)
   !$omp end master

   !$omp parallel private(myid)
   myid =omp_get_thread_num()
   call sleepNprint(intArg(myid+1))
   !$omp end parallel
 contains

subroutine sleepNprint(nSeconds) integer::nSeconds

           call sleep(nSeconds)

print*,nSeconds end subroutine sleepNprint end program sleepSort </lang> Compile and Output:

gfortran -fopenmp sleepSort.f90 -o sleepSort
./sleepSort 0 3 1 4 1 5 9
0
1
1
3
4
5
9

FreeBASIC

Can't use FreeBASIC sleep since it halts the program. Instead it uses a second array filled with times based on the value of number, this array is check against the timer. If the timer is past the stored time the value is printed. <lang freebasic>' version 21-10-2016 ' compile with: fbc -s console ' compile with: fbc -s console -exx (for bondry check on the array's) ' not very well suited for large numbers and large array's ' positive numbers only

Sub sandman(sleepy() As ULong)

   Dim As Long lb = LBound(sleepy)
   Dim As Long ub = UBound(sleepy)
   Dim As Long i, count = ub
   Dim As Double wakeup(lb To ub)
   Dim As Double t = Timer
   For i = lb To ub
       wakeup(i) = sleepy(i) +1 + t
   Next
   Do
       t = Timer
       For i = lb To ub
           If wakeup(i) <= t Then
               Print Using "####";sleepy(i);
               wakeup(i) = 1e9 ' mark it as used
               count = count -1
           End If
       Next
       Sleep (1 - (Timer - t)) * 300, 1 ' reduce CPU load
   Loop Until count < lb

End Sub

' ------=< MAIN >=------

Dim As ULong i, arr(10) Dim As ULong lb = LBound(arr) Dim As ULong ub = UBound(arr)

Randomize Timer For i = lb To ub -1 ' leave last one zero

   arr(i) = Int(Rnd * 10) +1

Next

Print "unsorted "; For i = lb To ub

   Print Using "####";arr(i);

Next Print : Print

Print " sorted "; sandman(arr())

Print : Print

' empty keyboard buffer While InKey <> "" : Wend Print : Print "hit any key to end program" Sleep End</lang>

Output:
unsorted     5   2   5   6   4   6   9   5   1   2   0

  sorted     0   1   2   2   4   5   5   5   6   6   9

Go

<lang go>package main

import ( "fmt" "log" "os" "strconv" "time" )

func main() { out := make(chan uint64) for _, a := range os.Args[1:] { i, err := strconv.ParseUint(a, 10, 64) if err != nil { log.Fatal(err) } go func(n uint64) { time.Sleep(time.Duration(n) * time.Millisecond) out <- n }(i) } for _ = range os.Args[1:] { fmt.Println(<-out) } }</lang> Usage and output:

./sleepsort 3 1 4 1 5 9
1
1
3
4
5
9

Using sync.WaitGroup

<lang go>package main

import (

       "fmt"
       "log"
       "os"
       "strconv"
       "sync"
       "time"

)

func main() {

       var wg sync.WaitGroup
       wg.Add(len(os.Args[1:]))
       for _,i := range os.Args[1:] {
               x, err := strconv.ParseUint(i, 10, 64)
               if err != nil {
                       log.Println(err)
               }
               wg.Add(1)
               go func(i uint64, wg *sync.WaitGroup) {
                       defer wg.Done()
                       time.Sleep(time.Duration(i) * time.Second)
                       fmt.Println(i)
               }(x, &wg)
       }
       wg.Wait()

}</lang>

Usage and output are the same as the version using channels. Note that the original version would sleep for increments of 1 full second, so I made my code do the same.

Groovy

<lang groovy> @Grab(group = 'org.codehaus.gpars', module = 'gpars', version = '1.2.1') import groovyx.gpars.GParsPool

GParsPool.withPool args.size(), {

   args.eachParallel {
       sleep(it.toInteger() * 10)
       println it
   }

} </lang>

Sample Run:

> groovy sleepsort.groovy 42 23 16 15 8 4
4
8
15
16
23
42

Haskell

<lang haskell>import System.Environment import Control.Concurrent import Control.Monad

sleepSort :: [Int] -> IO () sleepSort values = do

       chan <- newChan
       forM_ values (\time -> forkIO (threadDelay (50000 * time) >> writeChan chan time))
       forM_ values (\_ -> readChan chan >>= print)

main :: IO () main = getArgs >>= sleepSort . map read</lang>

Using mapConcurrently_

<lang haskell>import System.Environment import Control.Concurrent import Control.Concurrent.Async

sleepSort :: [Int] -> IO () sleepSort = mapConcurrently_ (\x -> threadDelay (x*10^4) >> print x)

main :: IO () main = getArgs >>= sleepSort . map read</lang>

This is problematic for inputs with multiple duplicates like [1,2,3,1,4,1,5,1] because simultaneous prints are done concurrently and the 1s and newlines get output in jumbled up order. The channels-based version above doesn't have this problem.

Icon and Unicon

The following solution only works in Unicon.

<lang unicon>procedure main(A)

   every insert(t:=set(),mkThread(t,!A))
   every spawn(!t)    # start threads as closely grouped as possible
   while (*t > 0) do write(<<@)

end

procedure mkThread(t,n) # 10ms delay scale factor

   return create (delay(n*10),delete(t,&current),n@>&main)

end</lang>

Sample run:

->ss 3 1 4 1 5 9 2 6
1
1
2
3
4
5
6
9
->

J

Works with: J version 903+

<lang J>scheduledumb=: {{

 id=:'dumb',":x:6!:9
 wd 'pc ',id  
 (t)=: u {{u y[erase n}} t=. id,'_timer'
 wd 'ptimer ',":n p.y

}}


ssort=: {{

 R=: 
 poly=. 1,>./ y
 poly{{ y{{R=:R,m[y}}scheduledumb m y}}"0 y
 Template:Echo R scheduledumb poly"0 >:>./ y
 EMPTY

}}</lang>

Task example:

<lang J> t=: ?~30

  t

11 7 22 16 17 2 1 19 23 29 9 21 15 10 12 27 3 4 24 20 14 5 26 18 8 6 0 13 25 28

  ssort t

0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29</lang>

Note that since t is the result of an RNG, the order of values in t would be different in subsequent attempts. For example:

<lang J> t=: ?~30

  t

23 26 24 25 10 12 4 5 7 27 16 17 14 8 3 15 18 13 19 21 2 28 22 9 6 20 11 1 29 0

  ssort t

0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29</lang>

Java

Works with: Java version 1.5+

<lang java5>import java.util.concurrent.CountDownLatch;

public class SleepSort { public static void sleepSortAndPrint(int[] nums) { final CountDownLatch doneSignal = new CountDownLatch(nums.length); for (final int num : nums) { new Thread(new Runnable() { public void run() { doneSignal.countDown(); try { doneSignal.await();

//using straight milliseconds produces unpredictable //results with small numbers //using 1000 here gives a nifty demonstration Thread.sleep(num * 1000); System.out.println(num); } catch (InterruptedException e) { e.printStackTrace(); } } }).start(); } } public static void main(String[] args) { int[] nums = new int[args.length]; for (int i = 0; i < args.length; i++) nums[i] = Integer.parseInt(args[i]); sleepSortAndPrint(nums); } }</lang> Output (using "3 1 4 5 2 3 1 6 1 3 2 5 4 6" as arguments):

1
1
1
2
2
3
3
3
4
4
5
5
6
6

JavaScript

<lang javascript>Array.prototype.timeoutSort = function (f) { this.forEach(function (n) { setTimeout(function () { f(n) }, 5 * n) }); } </lang> Usage and output: <lang javascript>[1, 9, 8, 7, 6, 5, 3, 4, 5, 2, 0].timeoutSort(function(n) { document.write(n + '
'); })</lang>

0
1
2
3
4
5
6
7
8
9

<lang javascript>Array.prototype.sleepSort = function(callback) {

 const res = [];
 for (let n of this)
   setTimeout(() => {
     res.push(n);
     if (this.length === res.length)
       callback(res);
   }, n + 1);
 return res;

};

[1, 9, 8, 7, 6, 5, 3, 4, 5, 2, 0].sleepSort(console.log); // [ 1, 0, 2, 3, 4, 5, 5, 6, 7, 8, 9 ] </lang>

jq

Translation of: Brainf***

Doesn't actually sleep. Instead, iterates reducing the values by one until each is zero.

<lang jq>echo '[5, 1, 3, 2, 11, 6, 4]' | jq ' def f:

 if .unsorted == [] then
   .sorted
 else
   { unsorted: [.unsorted[] | .t = .t - 1 | select(.t != 0)]
   , sorted: (.sorted + [.unsorted[] | .t = .t - 1 | select(.t == 0) | .v]) }
   | f
 end;

{unsorted: [.[] | {v: ., t: .}], sorted: []} | f | .[] '</lang>

Output:
1
2
3
4
5
6
11

Julia

Works with: Julia version 1.6

<lang julia>function sleepsort(V::Vector{T}) where {T <: Real}

   U = Vector{T}()
   sizehint!(U, length(V))
   @sync for v in V
       @async begin
           sleep(abs(v))
           (v < 0 ? pushfirst! : push!)(U, v)
       end
   end
   return U

end


v = rand(-10:10, 10) println("# unordered: $v\n -> ordered: ", sleepsort(v))</lang>

Output:
# unordered: [10, -1, 3, -9, 1, -5, -8, -7, -3, 3]
 -> ordered: [-9, -8, -7, -5, -3, -1, 1, 3, 3, 10]

Kotlin

<lang scala>// version 1.1.51

import kotlin.concurrent.thread

fun sleepSort(list: List<Int>, interval: Long) {

   print("Sorted  : ")
   for (i in list) {
       thread {
           Thread.sleep(i * interval)
           print("$i ")
       }
   }
   thread { // print a new line after displaying sorted list
       Thread.sleep ((1 + list.max()!!) * interval)
       println()
   }

}

fun main(args: Array<String>) {

  val list = args.map { it.toInt() }.filter { it >= 0 } // ignore negative integers
  println("Unsorted: ${list.joinToString(" ")}")
  sleepSort(list, 50)

}</lang>

Sample output:

$ java -jar sleepsort.jar 5 7 -1 2 4 1 8 0 3 9 6 
Unsorted: 5 7 2 4 1 8 0 3 9 6
Sorted  : 0 1 2 3 4 5 6 7 8 9 

Lua

Here's a slow implementation using only stock C Lua:

<lang lua>function sleeprint(n)

 local t0 = os.time()
 while os.time() - t0 <= n do
   coroutine.yield(false)
 end
 print(n)
 return true

end

coroutines = {} for i=1, #arg do

 wrapped = coroutine.wrap(sleeprint)
 table.insert(coroutines, wrapped)
 wrapped(tonumber(arg[i]))

end

done = false while not done do

 done = true
 for i=#coroutines,1,-1 do
   if coroutines[i]() then
     table.remove(coroutines, i)
   else
     done = false
   end
 end

end</lang>

By installing LuaSocket, you can get better than 1-second precision on the clock, and therefore faster output:

<lang lua>socket = require 'socket'

function sleeprint(n)

 local t0 = socket.gettime()
 while (socket.gettime() - t0)*100 <= n do
   coroutine.yield(false)
 end
 print(n)
 return true

end

coroutines = {} for i=1, #arg do

 wrapped = coroutine.wrap(sleeprint)
 table.insert(coroutines, wrapped)
 wrapped(tonumber(arg[i]))

end

done = false while not done do

 done = true
 for i=#coroutines,1,-1 do 
   if coroutines[i]() then
     table.remove(coroutines, i)
   else
     done = false
   end
 end

end</lang>

Either way, the output is the same:

Output:
$ lua sleep_sort.lua 3 1 4 1 5 9 2 6 5 3 5
1
1
2
3
3
4
5
5
5
6
9

Mathematica/Wolfram Language

<lang mathematica>SleepSort = RunScheduledTask[Print@#, {#, 1}] & /@ # &; SleepSort@{1, 9, 8, 7, 6, 5, 3, 4, 5, 2, 0};</lang>

Output:
0
1
2
3
4
5
6
7
8
9

NetRexx

As implemented this sample goes beyond the scope of the task as defined; it will handle negative numbers.

<lang NetRexx>/* NetRexx */ options replace format comments java crossref symbols nobinary import java.util.concurrent.CountDownLatch

-- ============================================================================= class RSortingSleepsort

 properties constant private
   dflt = '-6 3 1 4 5 2 3 -7 1 6 001 3 -9 2 5 -009 -8 4 6 1 9 8 7 6 5 -7 3 4 5 2 0 -2 -1 -5 -4 -3 -0 000 0'
 properties indirect
   startLatch = CountDownLatch
   doneLatch  = CountDownLatch
   floor      = 0
   sorted     = 
 -- ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
 method main(args = String[]) public static
   arg = Rexx(args)
   if arg =  then arg = dflt
   say ' unsorted:' arg
   say '   sorted:' (RSortingSleepsort()).sleepSort(arg)
   return
 -- ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
 method sleepSort(iArg) public
   setStartLatch(CountDownLatch(1))           -- used to put all threads on hold until we're ready to run
   setDoneLatch(CountDownLatch(iArg.words())) -- used to indicate all work is done
   loop mn = 1 to iArg.words()
     setFloor(getFloor().min(iArg.word(mn)))   -- save smallest -ve number so we can use it as a scale for sleep
     Thread(SortThread(iArg.word(mn))).start() -- loop through input and create a thread for each element
     end mn
   getStartLatch().countDown() -- cry 'Havoc', and let slip the dogs of war.
   do
     getDoneLatch().await() -- wait for worker threads to complete
   catch ix = InterruptedException
     ix.printStackTrace()
   end
   return getSorted()

-- ============================================================================= class RSortingSleepsort.SortThread dependent implements Runnable

 properties indirect
   num
 -- ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
 method SortThread(nm)
   setNum(nm)
   return
 -- ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
 method run() public
   do
     parent.getStartLatch().await()                 -- wait until all threads are constructed
     sleepTime = getNum() + parent.getFloor().abs() -- shifted by value of smallest number (permits numbers < 0)
     sleepTime = sleepTime * 250                    -- scale up; milliseconds are not granular enough
     Thread.sleep(sleepTime)                        -- wait for this number's turn to run
   catch ie = InterruptedException
     ie.printStackTrace()
   end
   do protect parent -- lock the parent to prevent collisions
     parent.setSorted((parent.getSorted() num).strip()) -- stow the number in the results List
   end
   parent.getDoneLatch().countDown() -- this one's done; decrement the latch
   return

</lang> Output:

 unsorted: -6 3 1 4 5 2 3 -7 1 6 001 3 -9 2 5 -009 -8 4 6 1 9 8 7 6 5 -7 3 4 5 2 0 -2 -1 -5 -4 -3 -0 000 0
   sorted: -9 -009 -8 -7 -7 -6 -5 -4 -3 -2 -1 000 0 0 -0 1 1 001 1 2 2 2 3 3 3 3 4 4 4 5 5 5 5 6 6 6 7 8 9

Nim

Compile with nim --threads:on c sleepsort: <lang nim>import os, strutils

proc single(n: int) =

 sleep n
 echo n

proc main =

 var thr = newSeq[TThread[int]](paramCount())
 for i,c in commandLineParams():
   thr[i].createThread(single, c.parseInt)
 thr.joinThreads

main()</lang> Usage:

$ ./sleepsort 5 1 3 2 11 6 4
1
2
3
4
5
6
11

Objeck

<lang objeck> use System.Concurrency; use Collection;

bundle Default {

 class Item from Thread {
   @value : Int;
   
   New(value : Int) {
     Parent();
     @value := value;
   }
   method : public : Run(param : System.Base) ~ Nil {
     Sleep(1000 * @value);
     @value->PrintLine();
   }
 }
 class SleepSort {
   function : Main(args : String[]) ~ Nil {
     items := Vector->New();
     each(i : args) {
       items->AddBack(Item->New(args[i]->ToInt()));
     };
   
     each(i : items) {
       items->Get(i)->As(Item)->Execute(Nil);
     };
   }
 }

} </lang>

Objective-C

<lang objc>#import <Foundation/Foundation.h>

int main(int argc, char **argv) {

   NSOperationQueue *queue = [[NSOperationQueue alloc] init];
   while (--argc) {
       int i = atoi(argv[argc]);
       [queue addOperationWithBlock: ^{
           sleep(i);
           NSLog(@"%d\n", i);
       }];
   }
   [queue waitUntilAllOperationsAreFinished];

}</lang> Rather than having multiple operations that sleep, we could also dispatch the tasks after a delay: <lang objc>#import <Foundation/Foundation.h>

int main(int argc, char **argv) {

   while (--argc) {
       int i = atoi(argv[argc]);
       dispatch_after(dispatch_time(DISPATCH_TIME_NOW, i * NSEC_PER_SEC),
                      dispatch_get_main_queue(),
                      ^{ NSLog(@"%d\n", i); });
   }

}</lang>

Oforth

Instead of printing numbers, each task sends its integer into a channel (after sleeping 20 * n milliseconds). This allows the main task to create a new sorted list with those integers.

20 milliseconds is used to (try to) handle scheduler tick on Windows systems (around 15 ms). On Linux systems (after kernel 2.6.8), this value can be smaller.

<lang Oforth>import: parallel

sleepSort(l)

| ch n |

  Channel new ->ch
  l forEach: n [ #[ n dup 20 * sleep ch send drop ] & ]
  ListBuffer newSize(l size) #[ ch receive over add ] times(l size) ;</lang>
Output:
100 seq 100 seq + sleepSort println
[1, 1, 2, 2, 3, 3, 4, 4, 5, 5, 6, 6, 7, 7, 8, 8, 9, 9, 10, 10, 11, 11, 12, 12, 13, 13, 14,
 14, 15, 15, 16, 16, 17, 17, 18, 18, 19, 19, 20, 20, 21, 21, 22, 22, 23, 23, 24, 24, 25, 2
5, 26, 26, 27, 27, 28, 28, 29, 29, 30, 30, 31, 31, 32, 32, 33, 33, 34, 34, 35, 35, 36, 36,
 37, 37, 38, 38, 39, 39, 40, 40, 41, 41, 42, 42, 43, 43, 44, 44, 45, 45, 46, 46, 47, 47, 4
8, 48, 49, 49, 50, 50, 51, 51, 52, 52, 53, 53, 54, 54, 55, 55, 56, 56, 57, 57, 58, 58, 59,
 59, 60, 60, 61, 61, 62, 62, 63, 63, 64, 64, 65, 65, 66, 66, 67, 67, 68, 68, 69, 69, 70, 7
0, 71, 71, 72, 72, 73, 73, 74, 74, 75, 75, 76, 76, 77, 77, 78, 78, 79, 79, 80, 80, 81, 81,
 82, 82, 83, 83, 84, 84, 85, 85, 86, 86, 87, 87, 88, 88, 89, 89, 90, 90, 91, 91, 92, 92, 9
3, 93, 94, 94, 95, 95, 96, 96, 97, 97, 98, 98, 99, 99, 100, 100]

Ol

<lang scheme> (define (sleep-sort lst)

  (for-each (lambda (timeout)
        (async (lambda ()
           (sleep timeout)
           (print timeout))))
     lst))

(sleep-sort '(5 8 2 7 9 10 5)) </lang>

Output:
2
5
5
7
8
9
10

Pascal

Works with: Free Pascal

my limit under linux was 4000 threads nearly 2 GB. <lang pascal> program sleepsort; {$IFDEF FPC}

 {$MODE DELPHI} {$Optimization ON,ALL}

{$ElSE}

 {$APPTYPE CONSOLE}

{$ENDIF} uses

 {$IFDEF UNIX}
 cthreads,
 {$ENDIF}
 SysUtils;

const

 HiLimit = 40;

type

 tCombineForOneThread = record
   cft_count : Uint64;
   cft_ThreadID: NativeUint;
   cft_ThreadHandle: NativeUint;
 end;
 pThreadBlock = ^tCombineForOneThread;

var

 SortIdx : array of INteger;
 ThreadBlocks : array of tCombineForOneThread;
 gblThreadCount,
 Finished: Uint32;
 procedure PrepareThreads(thdCount:NativeInt);
 var
   i : NativeInt;
 Begin
   For i := 0 to thdCount-1 do
     ThreadBlocks[i].cft_count:= random(2*HiLimit);
 end;
 procedure TestRunThd(parameter: pointer);
 var
    pThdBlk: pThreadBlock;
    fi: NativeInt;
 begin
   pThdBlk := @ThreadBlocks[NativeUint(parameter)];
   with pThdBlk^ do
   begin
     sleep(40*cft_count+1);
     fi := Finished-1;
     //write(fi:5,cft_count:8,#13); 
     InterLockedDecrement(Finished);
     SortIdx[fi]:= NativeUint(parameter);
   end;
   EndThread(0);
 end;
 procedure Test;
 var
   j,UsedThreads: NativeInt;
 begin
   randomize;
   UsedThreads:= GblThreadCount;
   Finished :=UsedThreads;
   PrepareThreads(UsedThreads);
   j := 0;
   while (j < UsedThreads) do
   begin
     with ThreadBlocks[j] do
       begin
         cft_ThreadHandle :=
         BeginThread(@TestRunThd, Pointer(j), cft_ThreadID,16384 {stacksize} );
         If cft_ThreadHandle = 0 then break;
       end;
     Inc(j);
   end;
   writeln(j);
   UsedThreads := j;
   Finished :=UsedThreads;
   repeat
     sleep(1);
   until finished = 0;
   For j := 0 to  UsedThreads-1 do
     CloseThread(ThreadBlocks[j].cft_ThreadID);
   //output of sleep-sorted data
   For j := UsedThreads-1 downto 1 do
     write(ThreadBlocks[SortIdx[j]].cft_count,',');
   writeln(ThreadBlocks[SortIdx[0]].cft_count);
 end;


begin

 randomize;
 gblThreadCount := Hilimit;
 Writeln('Testthreads : ',gblThreadCount);
 setlength(ThreadBlocks,gblThreadCount);
 setlength(SortIdx,gblThreadCount);
 Test;
 setlength(ThreadBlocks, 0);
 {$IFDEF WINDOWS}
 readln;
 {$ENDIF}

end.</lang>

Output:
time ./sleepsort
Testthreads : 40
40
1,8,9,10,11,12,12,13,14,18,24,24,24,26,28,35,35,37,42,49,50,52,54,54,56,57,59,60,61,62,64,69,69,71,72,73,76,77,78,79

real	0m3,164s

Perl

Basically the C code. <lang Perl>1 while ($_ = shift and @ARGV and !fork); sleep $_; print "$_\n"; wait;</lang>


A more optimal solution makes use of Coro, a cooperative threading library. It has the added effect of being much faster, fully deterministic (sleep is not exact), and it allows you to easily collect the return value: <lang Perl>use Coro; $ret = Coro::Channel->new; @nums = qw(1 32 2 59 2 39 43 15 8 9 12 9 11);

for my $n (@nums){ async { Coro::cede for 1..$n; $ret->put($n); } }

print $ret->get,"\n" for 1..@nums;</lang>

Phix

Based on Euphoria

without js -- (multitasking)
integer count
 
procedure sleeper(integer key)
    ? key -- (or maybe res &= key)
    count -= 1
end procedure
 
--sequence s = command_line()[3..$]
sequence s = split("3 1 4 1 5 9 2 6 5")
if length(s)=0 then
    puts(1,"Nothing to sort.\n")
else
    count = 0
    for i=1 to length(s) do
        object si = to_number(s[i])
        if integer(si) then
            atom task = task_create(sleeper,{si})
            task_schedule(task,{si/10,si/10})
            count += 1
        end if
    end for
 
    while count do
        task_yield()
    end while
end if

PicoLisp

Sleeping in main process

<lang PicoLisp>(de sleepSort (Lst)

  (make
     (for (I . N) Lst
        (task (- I) (* N 100)  N N  I I
           (link N)
           (pop 'Lst)
           (task (- I)) ) )
     (wait NIL (not Lst)) ) )</lang>

Sleeping in child processes

<lang PicoLisp>(de sleepSort (Lst)

  (make
     (for N Lst
        (task (pipe (wait (* N 100))) N N
           (link N)
           (pop 'Lst)
           (task (close @)) ) )
     (wait NIL (not Lst)) ) )</lang>

Output in both cases:

: (sleepSort (3 1 4 1 5 9 2 6 5))
-> (1 1 2 3 4 5 5 6 9)

Just printing (no sorted result list)

Basically the C code. <lang PicoLisp>(for N (3 1 4 1 5 9 2 6 5)

  (unless (fork)
     (call 'sleep N)
     (msg N)
     (bye) ) )</lang>

Output:

1              
1
2
3
4
5
5
6
9

Pike

<lang Pike>

  1. !/usr/bin/env pike

int main(int argc, array(string) argv) {

       foreach(argv[1..], string value)
       {
               int v = (int)value;
               if(v<0)
                       continue;
               call_out(print, v, value);
       }
       return -1;

}

void print(string value) {

       write("%s\n", value);
       if(find_call_out(print)==-1)
               exit(0);
       return;

} </lang> Output :

$ ./sleep-sort.pike 4 5 -3 1 2 7 6
1
2
4
5
6
7

Prolog

Works with SWI-Prolog. <lang Prolog>sleep_sort(L) :- thread_pool_create(rosetta, 1024, []) , maplist(initsort, L, LID), maplist(thread_join, LID, _LStatus), thread_pool_destroy(rosetta).

initsort(V, Id) :- thread_create_in_pool(rosetta, (sleep(V), writeln(V)), Id, []).

</lang> Output :

 sleep_sort([5, 1, 3, 2, 11, 6, 3, 4]).
1
2
3
3
4
5
6
11
true.

PureBasic

<lang PureBasic>NewMap threads()

Procedure Foo(n)

 Delay(n)
 PrintN(Str(n))

EndProcedure

If OpenConsole()

 For i=1 To CountProgramParameters()
   threads(Str(i)) = CreateThread(@Foo(), Val(ProgramParameter()))
 Next
 
 ForEach threads()
   WaitThread(threads())
 Next
 Print("Press ENTER to exit"): Input()

EndIf</lang>

Sleep_sort.exe 3 1 4 1 5 9
1
1
3
4
5
9
Press ENTER to exit

Python

Python: Using threading.Timer

<lang python>from time import sleep from threading import Timer

def sleepsort(values):

   sleepsort.result = []
   def add1(x):
       sleepsort.result.append(x)
   mx = values[0]
   for v in values:
       if mx < v: mx = v
       Timer(v, add1, [v]).start()
   sleep(mx+1)
   return sleepsort.result

if __name__ == '__main__':

   x = [3,2,4,7,3,6,9,1]
   if sleepsort(x) == sorted(x):
       print('sleep sort worked for:',x)
   else:
       print('sleep sort FAILED for:',x)</lang>
Sample output
sleep sort worked for: [3, 2, 4, 7, 3, 6, 9, 1]

Python v3.5+: Using asyncio

Since the introduction of async/await syntax, the implementation could be a sole translation from the original version in Bash:

Works with: Python 3.5+

<lang python>#!/usr/bin/env python3 from asyncio import run, sleep, wait from sys import argv

async def f(n):

   await sleep(n)
   print(n)

if __name__ == '__main__':

   run(wait(map(f, map(int, argv[1:]))))</lang>

Example usage:

$ ./sleepsort.py 5 3 6 3 6 3 1 4 7
1
3
3
3
4
5
6
6
7

Racket

<lang racket>

  1. lang racket
accepts a list to sort

(define (sleep-sort lst)

 (define done (make-channel))
 (for ([elem lst])
   (thread 
    (λ () 
      (sleep elem)
      (channel-put done elem))))
 (for/list ([_ (length lst)])
   (channel-get done)))
outputs '(2 5 5 7 8 9 10)

(sleep-sort '(5 8 2 7 9 10 5)) </lang>

Raku

(formerly Perl 6)

<lang perl6>await map -> $delay { start { sleep $delay ; say $delay } },

   <6 8 1 12 2 14 5 2 1 0>;</lang>
Output:
0
1
1
2
2
5
6
8
12
14

This can also be written using reactive programming:

<lang perl6>#!/usr/bin/env raku use v6; react whenever Supply.from-list(@*ARGS).start({ .&sleep // +$_ }).flat { .say }</lang>

Output:
$ ./sleep-sort 1 3 5 6 2 4
1
2
3
4
5
6

REXX

This sort will accept any manner of numbers,   or for that matter,   any character string as well.
REXX isn't particular what is being sorted. <lang rexx>/*REXX program implements a sleep sort (with numbers entered from the command line (CL).*/ numeric digits 300 /*over the top, but what the hey! */

                                                /*  (above)  ··· from vaudeville.      */

@.= /*placeholder for the array of numbers.*/ stuff= 1e9 50 5 40 4 1 100 30 3 12 2 8 9 7 6 6 10 20 0 /*alphabetically ··· so far.*/ parse arg numbers /*obtain optional arguments from the CL*/ if numbers= then numbers= stuff /*Not specified? Then use the default.*/ N= words(numbers) /*N is the number of numbers in list. */ w= length(N) /*width of N (used for nice output). */ parse upper version !ver . /*obtain which REXX we're running under*/ !regina= ('REXX-REGINA'==left(!ver, 11) ) /*indicate (or not) if this is Regina. */ say N 'numbers to be sorted:' numbers /*informative informational information*/

                                                /*from department of redundancy depart.*/
   do j=1  for N                                /*let's start to boogie─woogie da sort.*/
   @.j= word(numbers, j)                        /*plug in a single number at a time.   */
   if datatype(@.j, 'N')  then @.j= @.j / 1     /*normalize it if it's a numeric number*/
   if !regina  then call fork                   /*only REGINA REXX supports  FORK  BIF.*/
   call sortItem j                              /*start a sort for an array number.    */
   end   /*j*/
     do forever  while \inOrder(N)              /*wait for the sorts to complete.      */
     call delay 1                               /*one second is minimum effective time.*/
     end    /*forever while*/                   /*well heck,  other than zero seconds. */

m= max(length(@.1), length(@.N) ) /*width of smallest or largest number. */ say; say 'after sort:' /*display a blank line and a title. */

     do k=1  for N                              /*list the  (sorted)  array's elements.*/
     say left(, 20)     'array element'      right(k, w)      '───►'      right(@.k, m)
     end   /*k*/

exit /*stick a fork in it, we're all done. */ /*──────────────────────────────────────────────────────────────────────────────────────*/ sortItem: procedure expose @.; parse arg ? /*sorts a single (numeric) item. */

             do Asort=1  until \switched        /*sort unsorted array until it's sorted*/
             switched= 0                        /*it's all hunky─dorey, happy─dappy ···*/
                                    do i=1   while   @.i\==  &  \switched
                                    if @.? >= @.i then iterate     /*item is in order. */
                                    parse value   @.?  @.i     with     @.i  @.?
                                    switched= 1                    /* [↑]  swapped one.*/
                                    end   /*i*/
             if Asort//?==0  then call delay switched              /*sleep if last item*/
             end   /*Asort*/
         return               /*Sleeping Beauty awakes.  Not to worry:  (c)=circa 1697.*/

/*──────────────────────────────────────────────────────────────────────────────────────*/ inOrder: procedure expose @.; parse arg howMany /*is the array in numerical order? */

          do m=1  for howMany-1;  next= m+1;  if @.m>@.next  then return 0 /*¬ in order*/
          end   /*m*/                           /*keep looking for fountain of youth.  */
        return 1                                /*yes, indicate with an indicator.     */</lang>

Programming note:   this REXX program makes use of   DELAY   BIF which delays (sleeps) for a specified amount of seconds.
Some REXXes don't have a   DELAY   BIF,   so one is included here   ──►   DELAY.REX.


output   when using the internal default input:
19 numbers to be sorted: 1E9 50 5 40 4 1 100 30 3 12 2 8 9 7 6 6 10 20 0

after sort:
                     array element  1 ───►          0
                     array element  2 ───►          1
                     array element  3 ───►          2
                     array element  4 ───►          3
                     array element  5 ───►          4
                     array element  6 ───►          5
                     array element  7 ───►          6
                     array element  8 ───►          6
                     array element  9 ───►          7
                     array element 10 ───►          8
                     array element 11 ───►          9
                     array element 12 ───►         10
                     array element 13 ───►         12
                     array element 14 ───►         20
                     array element 15 ───►         30
                     array element 16 ───►         40
                     array element 17 ───►         50
                     array element 18 ───►        100
                     array element 19 ───► 1000000000

Ruby

<lang ruby>require 'thread'

nums = ARGV.collect(&:to_i) sorted = [] mutex = Mutex.new

threads = nums.collect do |n|

 Thread.new do
   sleep 0.01 * n
   mutex.synchronize {sorted << n}
 end

end threads.each {|t| t.join}

p sorted</lang>

Example

$ ruby sleepsort.rb 3 1 4 5 2 3 1 6 1 3 2 5 4 6
[1, 1, 1, 2, 2, 3, 3, 3, 4, 4, 5, 5, 6, 6]

Rust

<lang rust>use std::thread;

fn sleepsort<I: Iterator<Item=u32>>(nums: I) {

   let threads: Vec<_> = nums.map(|n|
       thread::spawn(move || {
           thread::sleep_ms(n);
           println!("{}", n); })).collect();
   for t in threads { t.join(); }

}

fn main() {

   sleepsort(std::env::args().skip(1).map(|s| s.parse().unwrap()));

}</lang> Output:

$ ./sleepsort 50 34 43 3 2
2
3
34
43
50

Scala

<lang scala>object SleepSort {

 def main(args: Array[String]): Unit = {
   val nums = args.map(_.toInt)
   sort(nums)
   Thread.sleep(nums.max * 21) // Keep the JVM alive for the example
 }
 def sort(nums: Seq[Int]): Unit =
   nums.foreach(i => new Thread {
     override def run() {
       Thread.sleep(i * 20) // just `i` is unpredictable with small numbers
       print(s"$i ")
     }
   }.start())

}</lang>

Output:

<lang bash>$ scala SleepSort 1 3 6 0 9 7 4 2 5 8 0 1 2 3 4 5 5 6 7 8 9 </lang>

Sidef

<lang ruby>ARGV.map{.to_i}.map{ |i|

   {Sys.sleep(i); say i}.fork;

}.each{.wait};</lang>

Output:
% sidef test.sf 5 1 3 2 11 6 4
1
2
3
4
5
6
11

Simula

<lang simula>SIMULATION BEGIN

   PROCESS CLASS SORTITEM(N); INTEGER N;
   BEGIN
       HOLD(N);
       OUTINT(N, 3);
   END;
   INTEGER I;
   FOR I := 3, 2, 4, 7, 3, 6, 9, 1 DO
   BEGIN
       REF(SORTITEM) SI;
       SI :- NEW SORTITEM(I);
       ACTIVATE SI;
   END;
   HOLD(100000);
   OUTIMAGE;

END;</lang>

Output:
  1  2  3  3  4  6  7  9

SNUSP

Bloated SNUSP is ideally suited to this task, since this the variant adds multithreading and an additional dimension of data space. Sleep time is simulated by the loop delay required to copy each cell value, thereby ensuring that smaller values are printed earlier than larger values. This program requires a Bloated SNUSP interpreter which returns zero on input end-of-file. <lang SNUSP>

     /$>\  input until eof
 #/?<\?,/  foreach: fork
  \ &/:+   copy and\
   /:\?-;    delay /
   \.#     print and exit thread

</lang>

Legend:

  • & - SPLIT creates a new thread. Like @ ENTER, it skips one cell of code space to start its continuation.
  • : ; - UP and DOWN are equivalent to < > LEFT and RIGHT, but moves the data pointer in the second dimension.
  • # - in Bloated SNUSP, LEAVE only terminates the current thread. The overall program only exits when all threads have quit.

Swift

<lang Swift>import Foundation

for i in [5, 2, 4, 6, 1, 7, 20, 14] {

   let time = dispatch_time(DISPATCH_TIME_NOW,
       Int64(i * Int(NSEC_PER_SEC)))
   
   dispatch_after(time, dispatch_get_main_queue()) {
       print(i)
   }

}

CFRunLoopRun()</lang>

Output:
1
2
4
5
6
7
14
20

Tcl

Tcl 8.5

<lang tcl>#!/bin/env tclsh set count 0 proc process val {

   puts $val
   incr ::count

}

  1. Schedule the output of the values

foreach val $argv {

   after [expr {$val * 10}] [list process $val]

}

  1. Run event loop until all values output...

while {$count < $argc} {

   vwait count

}</lang> Demo:

bash$ sleepsort.tcl 3 1 4 5 2 3 1 6 1 3 2 5 4 6
1
1
1
2
2
3
3
3
4
4
5
5
6
6

Tcl 8.6

<lang tcl>set sorted {} lmap x $argv {after $x [list lappend sorted $x]} while {[llength $sorted] != $argc} { vwait sorted } puts $sorted</lang>

Output:
$ echo 'puts [lmap _ [lrepeat 30 {}] {expr {int(rand() * 100)}}]' | tclsh | tee /dev/tty | xargs tclsh sleepsort.tcl
5 8 70 27 15 80 49 2 69 93 29 1 14 84 43 2 81 44 60 62 8 75 23 61 42 68 79 46 72 65
1 2 2 5 8 8 14 15 23 27 29 42 43 44 46 49 60 61 62 65 68 69 70 72 75 79 80 81 84 93

Tcl 8.6: coroutine

<lang tcl>#! /usr/bin/env tclsh

package require Tcl 8.6

  1. By aspect (https://wiki.tcl-lang.org/page/aspect). Modified slightly.
  2. 1. Schedule N delayed calls to our own coroutine.
  3. 2. Yield N times to grab the scheduled values. Print each.
  4. 3. Store the sorted list in $varName.

proc sleep-sort {ls varName} {

   foreach x $ls {
       after $x [info coroutine] $x
   }

   set $varName [lmap x $ls {
       set newX [yield]
       puts $newX
       lindex $newX
   }]

}

  1. Ensure the list is suitable for use with [sleep-sort].

proc validate ls {

   if {[llength $ls] == 0} {
       error {list is empty}
   }

   foreach x $ls {
       if {![string is integer -strict $x] || $x < 0} {
           error [list invalid value: $x]
       }        
   }

   return $ls

}

coroutine c sleep-sort [validate $argv] ::sorted vwait sorted</lang> Demo:

$ ./sleepsort.tcl 1 2 100 40 76 0 0 0 200 199
0
0
0
1
2
40
76
100
199
200

UNIX Shell

Works with: Bourne Shell

<lang bash>f() {

   sleep "$1"
   echo "$1"

} while [ -n "$1" ] do

   f "$1" &
   shift

done wait</lang> Usage and output:

sh sleepsort.sh 3 1 4 1 5 9
1
1
3
4
5
9

Visual Basic .NET

<lang vbnet>Imports System.Threading

Module Module1

   Sub SleepSort(items As IEnumerable(Of Integer))
       For Each item In items
           Task.Factory.StartNew(Sub()
                                     Thread.Sleep(1000 * item)
                                     Console.WriteLine(item)
                                 End Sub)
       Next
   End Sub
   Sub Main()
       SleepSort({1, 5, 2, 1, 8, 10, 3})
       Console.ReadKey()
   End Sub

End Module</lang>

Output:
1
1
2
3
5
8
10

Wren

More of a simulation than a 'true' sleep sort. <lang ecmascript>import "timer" for Timer import "io" for Stdout import "os" for Process

var args = Process.arguments var n = args.count if (n < 2) Fiber.abort("There must be at least two arguments passed.") var list = args.map{ |a| Num.fromString(a) }.toList if (list.any { |i| i == null || !i.isInteger || i < 0 } ) {

   Fiber.abort("All arguments must be non-negative integers.")

} var max = list.reduce { |acc, i| acc = (i > acc) ? i : acc } var fibers = List.filled(max+1, null) System.print("Before: %(list.join(" "))") for (i in list) {

   var sleepSort = Fiber.new { |i|
       Timer.sleep(1000)
       Fiber.yield(i)
   }
   fibers[i] = sleepSort

} System.write("After : ") for (i in 0..max) {

   var fib = fibers[i]
   if (fib) {
       System.write("%(fib.call(i)) ")
       Stdout.flush()
   }

} System.print()</lang>

Output:

Sample run:

$ wren sleepsort.wren  1 8 3 7 4 6
Before: 1 8 3 7 4 6
After : 1 3 4 6 7 8 

zkl

<lang zkl>vm.arglist.apply(fcn(n){ Atomic.sleep(n); print(n) }.launch); Atomic.waitFor(fcn{ vm.numThreads == 1 }); Atomic.sleep(2); println();</lang>

Output:
$ zkl bbb 7 6 9 2 4 8 1 3 5
123456789
$