排序整数列表


22

挑战

真的很简单,对数字列表进行排序。

细节

您必须按升序对数字列表进行排序,而不使用任何内置的排序函数/库/等(例如,list.sort()在Python中)。

输入/输出可以用您选择的任何方法完成,只要它是人类可读的即可。

一如既往,不允许出现标准漏洞。

以字节为单位的最短代码获胜。

您必须说明/列出您使用的排序方法(气泡,插入,选择等)。

输入将不包含重复项。

样本输入/输出

输入: 99,-2,53,4,67,55,23,43,88,-22,36,45

输出: -22,-2,4,23,36,43,45,53,55,67,88,99

注意:与“ 对数字列表排序”正好相反


8
如果不是重复的内容,我会感到非常惊讶,但是我没有时间检查。无论如何,应该更好地定义“内置排序功能”。可以使用索引所有值的函数吗?[7 2 4 1] -> [4 2 3 1]。另外,CSV列表可以放在方括号内吗?此外,特定的输入格式非常适合某些语言,而对其他语言则不利。这使得输入解析对于某些提交来说很重要,而对于其他提交则不需要。
Stewie Griffin

1
@StewieGriffin我见过很多排序难题,但没有一个仅处理基本的整数列表。对于某些语言而言,存在许多挑战,而在其他语言中则存在许多挑战。
Michelfrancis Bustillos

非常相似,但有一个O(n日志(N))的限制。
内森·美林

2
这个问题密切相关,但是由于此处的某些答案(例如Dennis的范围过滤)要求输入为整数,因此我不会投票将其作为重复项关闭。
彼得·泰勒

相关内容:youtube.com/user/AlgoRythmics/videos —一个YouTube频道,可通过匈牙利舞蹈教排序算法!
sergiol '17

Answers:


23

05AB1E,2个字节

码:

ϧ

Jelly答案相同的算法。计算输入的所有排列并弹出最小的排列。

在线尝试!


一种更有效的方法是:

E[ß,Ž

执行选择排序。使用CP-1252编码。

在线尝试!


6
暂时接受这个,因为我没有看到任何人得到小于2
Michelfrancis布斯蒂略斯

6
@MichelfrancisBustillos很好,如果他们做到了,那将是一个内置函数,不是吗?
破坏的柠檬

我刚才看了05AB1E / Base,然后看了看。巧合?
facepalm42

17

果冻,3个字节

Œ!Ṃ

这将生成输入列表的所有排列,然后选择字典上最小的排列。非常有效率。

归功于@Adnan,他们独立拥有相同的想法。

在线尝试!


果冻,4个字节

ṂrṀf

这将建立从最小列表到最大列表的范围,然后丢弃原始列表中不存在的范围元素。从技术上讲,这是一种水桶分类,具有非常小的水桶。我不知道此特定变体的名称。

在线尝试!

怎么运行的

ṂrṀf  Main link. Argument: A (list/comma-separated string)

Ṃ     Compute the minimum of A.
  Ṁ   Compute the maximum of A.
 r    Yield the inclusive range from the minimum to the maximum.
   f  Filter the range by presence in A.

O(非常)。使用很多排序。
mbomb007 '16

22
因此,O。非常有用。好多 惊奇!(对不起,什么?)
丹尼斯

我对算法的复杂性不是很好,这是O(n!)吗?
FlipTack

2
@FlipTack我也不是。可能更高一些,因为那里有n个!长度为n的数组。
丹尼斯,

1
因为每个n!数组必须按顺序进行比较,而字典上的比较则为O(n)。如果能够高效完成,生成也可以在O(n * n!)中完成,所以我敢打赌,如果实现
得当


9

Brachylog12 7字节

p.'(s>)

这使用了排列排序,这显然很糟糕,但是嘿,它比Pyth短!

说明

p.       Unifies the output with a permutation of the input
  '(  )  True if what's inside the parentheses cannot be proven, else backtrack and
         try with another permutation of the input.
    s    Take an ordered subset from the output
     >   True if the first element is bigger than the second (hence not sorted)
         We don't need to check that the subset is 2 elements long because > will be false
         for inputs that are not 2 elements long anyway

9

Haskell,38个字节

h%t|(a,b)<-span(<h)t=a++h:b
foldr(%)[]

二进制函数通过%将元素划分为元素的前缀和元素的后缀,将新元素h插入到排序列表中,并在它们之间插入。tta<hb>hh

foldr(%)[]然后,该操作通过从输入列表中反复插入元素来从空构建一个排序列表。

比直接递归实现短一个字节

f(h:t)|(a,b)<-span(<h)$f t=a++h:b
f x=x

41个字节的另一种策略:

f[]=[]
f l|x<-minimum l=x:f(filter(/=x)l)

因此,这是en.wikipedia.org/wiki/Insertion_sort%作为插入内部循环,并将foldr其应用为外部循环。
彼得·科德斯

8

JavaScript(ES6),51个字节

a=>a.map(_=>m=Math.min(...a.filter(e=>e>m)),m=-1/0)

每个循环查找到目前为止尚未找到的最小数字。


调用此上[1,2,3,4,5,4,3,2,1]产生[1, 2, 3, 4, 5, Infinity, Infinity, Infinity, Infinity]
本杰明Gruenbaum

@BenjaminGruenbaum“输入将不包含重复项。”
尼尔

我有一个不同的方法完全一样BYTECOUNT
巴林特

实际上少了1个字节
巴林特


8

Python 2,34个字节

def f(s):m=min(s);print m;f(s-{m})

将输入作为一组,按升序打印其元素,并终止于错误。

干净的终止可以用41个字节完成:

def f(s):
 if s:m=min(s);print m;f(s-{m})

要么

l=input()
while l:m=min(l);print m;l-={m}

输入可以作为39字节或Python 3.5中38字节的列表:

def f(l):m=min(l);print m;f(set(l)-{m})
def f(l):m=min(l);print(m);f({*l}-{m})

这是一个en.wikipedia.org/wiki/Selection_sort,使用m=min(s)/ s - (m)作为内部循环,以从未排序的元素中查找和删除最小值,并以递归作为外部。
彼得·科德斯

8

Haskell,42 41 38字节

f u=filter(`elem`u)[(minBound::Int)..]

循环遍历所有整数(在我的计算机上为带符号的64位),并保留其中的整数u。当然,它不会在合理的时间内完成。

循环通过的先前版本[minimum u..maximum u]具有相同的最坏情况运行时间。

编辑:@xnor保存了一个字节。谢谢!


filter是短一个:f u=filter(`elem`u)[minimum u..maximum u]
xnor

多么蛮力![minimum u..]由于类型原因不起作用?
xnor

@xnor:我是这样认为的。假设调用时,f [1,3,0]元素默认Integer为未绑定的类型,因此..永不结束。如果您必须这样称呼f ([1, 3, 0]::[Int])我,那么类型注释必须包含在字节数中。
nimi

它如何检测多次出现的元素?
feersum '16

1
@feersum:没有,但是挑战说:“输入将不包含重复项”。
nimi 2016年

8

Oracle SQL 11.2,205字节

WITH s AS(SELECT COLUMN_VALUE||''e FROM XMLTABLE(('"'||REPLACE(:1,',','","')||'"'))),v(p,f)AS(SELECT e,e FROM s UNION ALL SELECT p||','||e,e FROM v,s WHERE e+0>f)SELECT p FROM v WHERE LENGTH(p)=LENGTH(:1);         

未打高尔夫球

WITH 
s AS  -- Split the string using ',' as separator
(     -- ||'' cast the xml type to varchar
  SELECT COLUMN_VALUE||''e FROM XMLTABLE(('"'||REPLACE(:1,',','","')||'"'))
),  
v(p,f) AS  -- Recursive view : p = sorted string, f last number added
(
  SELECT e,e FROM s -- use each number as seed
  UNION ALL         -- only add a number if it is > the last added
  SELECT p||','||e,e FROM v,s WHERE e+0>f  -- +0 is needed to compare int and not strings
)  
-- The valid string has the same length as the input
SELECT p FROM v WHERE LENGTH(p)=LENGTH(:1)          

至于哪种排序方法,我不知道ORDER BY要确保忘记了。


我几乎不了解SQL,但是根据您的评论,我认为您是从其余未排序的元素中选择最小值或最大值,并将其追加到排序列表的末尾。这使它成为en.wikipedia.org/wiki/Selection_sort
彼得·科德斯

8

x86-16机器码(BubbleSort int8_t),20 19字节

x86-64 / 32机器码(JumpDownSort)21 19字节

变更日志:

  • 感谢@ ped7g的lodsb/ cmp [si],al想法,并将其与我一直在看的指针增量/重置放在一起。不需要al/ ah让我们对较大的整数使用几乎相同的代码。

  • 新的(但相关的)算法,实现方式有很多变化:Bubbly SelectionSort允许使用较小的x86-64实现字节或双字;在x86-16上达到收支平衡(字节或字)。还避免了我的BubbleSort出现的size = 1错误。见下文。

  • 事实证明,每次找到新的最小值时,带有交换的“气泡选择排序”已经是一种已知的算法JumpDown排序。在《泡泡排序:考古学算法分析》中提到了这一点(即,泡泡排序如何在吮吸时变得很流行)。


对8位有符号整数进行原位排序。(无符号是相同的代码大小,只需将更jge改为即可jae)。重复不是问题。我们使用16位旋转8进行交换(带有存储目标)。

Bubble Sort会降低性能,但是我已经读到它是在机器代码中最小的实现之一。当存在用于交换相邻元素的特殊技巧时,这似乎尤其正确。这几乎是它的唯一优势,但是有时(在现实生活中的嵌入式系统中)这足以将其用于非常短的列表。

我忽略了没有交换的提前终止。我使用了Wikipedia的“优化” BubbleSort循环,该循环避免在第-次n − 1运行时查看最后一个项目n,因此外循环计数器是内循环的上限。

NASM列表(nasm -l /dev/stdout),或纯来源

 2 address  16-bit       bubblesort16_v2:
 3          machine      ;; inputs: pointer in ds:si,  size in in cx
 4          code         ;; requires: DF=0  (cld)
 5          bytes        ;; clobbers: al, cx=0
 6                       
 7 00000000 49               dec     cx          ; cx = max valid index.  (Inner loop stops 1 before cx, because it loads i and i+1).
 8                       .outer:                 ; do{
 9 00000001 51               push    cx          ;   cx = inner loop counter = i=max_unsorted_idx
10                       .inner:                 ;   do{
11 00000002 AC               lodsb               ;     al = *p++
12 00000003 3804             cmp     [si],al     ;     compare with *p (new one)
13 00000005 7D04             jge     .noswap
14 00000007 C144FF08         rol     word [si-1], 8    ; swap
15                       .noswap:
16 0000000B E2F5             loop    .inner      ;   } while(i < size);
17 0000000D 59               pop     cx          ;  cx = outer loop counter
18 0000000E 29CE             sub     si,cx       ;  reset pointer to start of array
19 00000010 E2EF             loop    .outer      ; } while(--size);
20 00000012 C3               ret

22 00000013  size = 0x13 = 19 bytes.

cx围绕内部循环的push / pop 表示它以cx= external_cx降至0运行。

请注意,这 rol r/m16, imm8不是8086指令,它是在以后添加的(186或286),但这并不是要成为8086代码,而只是16位x86。如果SSE4.1 phminposuw有帮助,我会使用它。

此的32位版本(仍可在8位整数上运行,但具有32位指针/计数器)为20字节(上的操作数大小前缀rol word [esi-1], 8

错误:将size = 1视为size = 65536,因为没有什么会阻止我们在cx = 0时输入外部do /。(您通常会使用jcxz它。)但是幸运的是19字节的JumpDown排序是19字节,没有这个问题。


原始的x86-16 20字节版本(没有Ped7g的想法)。省略以节省空间,请参阅编辑历史记录以及说明。


性能

部分重叠的存储/重载(在内存目标旋转中)导致现代x86 CPU(有序Atom除外)上的存储转发停顿。当一个高的值向上冒泡时,这种额外的延迟是循环携带的依赖链的一部分。首先,存储/重载很烂(例如Haswell上的5个周期的存储转发延迟),但是转发停顿将其增加到13个周期以上。乱序执行将很难隐藏它。

另请参阅:堆栈溢出:冒泡排序,用于以类似的实现对此版本的字符串进行排序,但是不需要交换时可以提前淘汰。它使用xchg al, ah/ mov [si], ax进行交换,它长1个字节,并在某些CPU上导致部分寄存器停顿。(但是它可能仍然比memory-dst旋转更好,后者需要再次加载该值)。我的评论有一些建议...


x86-64 / x86-32 JumpDown排序,19个字节(对int32_t的排序)

可以使用x86-64 System V调用约定从C调用
int bubblyselectionsort_int32(int dummy, int *array, int dummy, unsigned long size); (返回值= max(array []))。

这是https://en.wikipedia.org/wiki/Selection_sort,但与其记住min元素的位置,不如将当前候选位置交换到array中。找到min(unsorted_region)后,将其存储到已排序区域的末尾,就像普通的Selection Sort一样。这样可使排序区域增加一个。(在代码中,rsi指向已排序区域末尾的一个;lodsd将其前进并将mov [rsi-4], eax最小值存储回去。)

泡沫排序中使用名称Jump Down Sort :考古学算法分析。我猜我的排序实际上是一个Jump Up排序,因为高元素向上跳,而底部排序而不是末尾排序。

这种交换设计导致数组的未排序部分最终以反向排序的顺序结束,此后导致大量交换。(因为您从一个较大的候选对象开始,并且不断看到越来越少的候选对象,所以您一直在交换。)我将其称为“气泡状”,即使它使元素向另一个方向移动。它移动元素的方式也有点像向后插入排序。要观看它的运行情况,请使用GDB的display (int[12])buf,在内部loop指令上设置一个断点,然后使用c(继续)。按回车重复。(“ display”命令使GDB每次遇到断点时都打印整个阵列状态)。

xchg使用mem有一个隐式lock前缀,这会使这特别慢。可能比有效的加载/存储交换慢大约一个数量级;xchg m,r在Skylake上,每23c吞吐量是一个,但是使用tmp reg进行加载/存储/移动以进行有效的swap(reg,mem)可以使每个时钟移动一个元素。在loop指令速度快并且不会对内部循环造成太大瓶颈的AMD CPU上,这可能是一个更糟糕的比率,但是分支未命中仍然是一个大瓶颈,因为交换很常见(随着未排序区域变小,这种情况会变得更加普遍。 )。

 2 Address               ;; hybrib Bubble Selection sort
 3        machine         bubblyselectionsort_int32:   ;; working, 19 bytes.  Same size for int32 or int8
 4        code               ;; input: pointer in rsi, count in rcx
 5        bytes              ;; returns: eax = max
 6                       
 7                           ;dec  ecx           ; we avoid this by doing edi=esi *before* lodsb, so we do redundant compares
 8                                               ; This lets us (re)enter the inner loop even for 1 element remaining.
 9                       .outer:
10                           ; rsi pointing at the element that will receive min([rsi]..[rsi+rcx])
11 00000000 56               push   rsi
12 00000001 5F               pop    rdi
13                           ;mov    edi, esi     ; rdi = min-search pointer
14 00000002 AD               lodsd
16 00000003 51               push   rcx          ; rcx = inner counter
17                       .inner:                   ; do {
18                           ; rdi points at next element to check
19                           ; eax = candidate min
20 00000004 AF               scasd                 ; cmp eax, [rdi++]
21 00000005 7E03             jle  .notmin
22 00000007 8747FC           xchg   [rdi-4], eax   ; exchange with new min.
23                         .notmin:
24 0000000A E2F8             loop  .inner          ; } while(--inner);
26                           ; swap min-position with sorted position
27                           ; eax = min.  If it's not [rsi-4], then [rsi-4] was exchanged into the array somewhere
28 0000000C 8946FC           mov    [rsi-4], eax
29 0000000F 59               pop   rcx           ; rcx = outer loop counter = unsorted elements left
30 00000010 E2EE             loop  .outer        ; } while(--unsorted);
32 00000012 C3               ret

34 00000013 13           .size: db $ - bubblyselectionsort_int32
           0x13 = 19 bytes long

相同的代码大小int8_t:使用lodsb/ scasbAL和变化[rsi/rdi-4]-1。相同的机器代码在32位模式下可用于8/32位元素。需要重新构建8/16位元素的16位模式,并更改偏移量(并且16位寻址模式使用不同的编码)。但仍然是19个字节。

dec ecx通过与继续前进之前刚加载的元素进行比较,它避免了初始值。在外循环的最后一次迭代中,它加载最后一个元素,检查它是否小于自身,然后完成。这使它可以与size = 1一起工作,而我的BubbleSort失败(将其处理为size = 65536)。

我使用以下调用者测试了此版本(在GDB中): 在线试用!。您可以在TIO上运行它,但是当然没有调试器或打印程序。不过,_start调用它的退出状态是exit-status =最大元素= 99,因此您可以看到它的工作原理。


内循环循环条件可能还有改进的空间,似乎使用了很多字节。也许同时推送/弹出cx和同时使用loop?也许以另一种方式循环,从数组的后面到数组的前面,以便我们将索引计数降至零?(并增加,bx因为已排序的部分位于循环的末尾)。
彼得·科德斯

1
降低到19B,但是进行了很多更改,还输入了输入规则(可能不需要进行某些更改,但是正如我在玩弄的那样,它们保留了较早的实验)...它仍然基于您的工作,因此不愿发布它作为答案,您可以在pastebin上进行检查:pastebin.com/0VMzdUjj
Ped7g

@ Ped7g:太好了!我曾考虑sub si, cx使用指针而不是索引来作为外部循环的一部分,但是我没有想到lodsb/ cmp [si], al。我一直在考虑lodsw/ dec si,或者lodsb/ xchg al,ah仍然打算参加cmp ah,al
Peter Cordes

@ Ped7g:哦,您的版本需要cld,或者我想我们可以将其作为调用约定的一部分。已DF清除的AFAIK 不是16位调用约定的标准部分,只有32/64。还是只是您不能在引导加载程序中使用它?但是,使用自定义寄存器调用约定,这和功能一样多,因此可以肯定,为什么不要求DF = 0。(如果需要,ES = DS,所以我们可以scasb代替它,lodsb这是更方便的方法。)
Peter Cordes

1
@ Ped7g:我不了解16位约定,我只知道您不能总是假定DF已清除。但是我认为这主要是在引导加载程序环境中。我从未在真正的DOS上运行过任何写过的东西。我当时使用的是Atari Mega 4 STe(68000/68020),然后是Linux(在奔腾MMX上),因此我设法完全避免使用16位x86,直到SO问题将其淹没为止。
彼得·科德斯

6

C,72个字节

i,j;a(int*l,int n){for(i=0;i=i?:--n;j>l[n]?l[i]=l[n],l[n]=j:0)j=l[--i];}

Bubblesort。第一个参数是指向数组的指针,第二个参数是数组的长度。与gcc一起使用。


这确实需要一个非高尔夫版本才能阅读;很难跟踪三元运算符的开始/结束位置。
彼得·科德斯

5

MATL11个10字节

Y@t!d0>AY)

对输入的所有排列的检查效率极低。

在线尝试!

说明

        % Implicitly grab input array
Y@      % Compute all permutations (each permutation as a row)
t       % Duplicate this matrix
!d      % Transpose and take the differences between the values
0>A     % Find the rows where all differences are > 0
Y)      % Return only the row where this is true
        % Implicitly display the result

5

Ruby,40个字节

选择排序。匿名函数;将列表作为参数。

->a{r=[];r<<a.delete(a.min)while[]!=a;r}

4

Python,120字节

def f(a):import time,threading;[threading.Thread(None,lambda b=b,c=min(a):print(time.sleep(b-c)or b)).start()for b in a]

这可能不是最短的答案,但是我觉得这个算法属于这里。用整数列表调用,它们将以有序方式打印到stdout。我不会尝试使用太大的数字。


不错的第一篇文章!还有很好的用户名。:P
Rɪᴋᴇʀ

4

MIPS,68个字节

不久前,我写了一个简单的未优化的冒泡排序实现。假定列表地址和列表长度已在内存中,则字节计数从开始于loop结束于li $v0, 10

 Address    Code        Basic                     Source

0x00400000  0x3c011001  lui $1,4097           5    main:   la      $s0, list       # List address
0x00400004  0x34300000  ori $16,$1,0               
0x00400008  0x2411000a  addiu $17,$0,10       6            li      $s1, 10         # List length
0x0040000c  0x24080000  addiu $8,$0,0         8    loop:   li      $t0, 0          # swapped
0x00400010  0x24090001  addiu $9,$0,1         9            li      $t1, 1          # for loop "i"
0x00400014  0x1131000b  beq $9,$17,11         11   for:    beq     $t1, $s1, fend  # break if i==length
0x00400018  0x00095080  sll $10,$9,2          13           sll     $t2, $t1, 2     # Temp index, multiply by 4
0x0040001c  0x01505020  add $10,$10,$16       14           add     $t2, $t2, $s0   # Combined address
0x00400020  0x8d4b0000  lw $11,0($10)         15           lw      $t3, 0($t2)     # list[i]
0x00400024  0x8d4cfffc  lw $12,-4($10)        16           lw      $t4, -4($t2)    # list[i-1]
0x00400028  0x21290001  addi $9,$9,1          18           addi    $t1, $t1, 1     # i++
0x0040002c  0x016c082a  slt $1,$11,$12        20           ble     $t4, $t3, for   # if list[i-1] > list[i]
0x00400030  0x1020fff8  beq $1,$0,-8               
0x00400034  0xad4bfffc  sw $11,-4($10)        21           sw      $t3, -4($t2)    # swap and store
0x00400038  0xad4c0000  sw $12,0($10)         22           sw      $t4, 0($t2)     
0x0040003c  0x24080001  addiu $8,$0,1         23           li      $t0, 1          # swapped=true
0x00400040  0x08100005  j 0x00400014          24           j       for
0x00400044  0x20010001  addi $1,$0,1          26   fend:   subi    $s1, $s1, 1     # length--
0x00400048  0x02218822  sub $17,$17,$1             
0x0040004c  0x1500ffef  bne $8,$0,-17         27           bnez    $t0, loop       # Repeat if swapped==true
0x00400050  0x2402000a  addiu $2,$0,10        29           li      $v0, 10        
0x00400054  0x0000000c  syscall               30           syscall

现在,我等待被x86吹走...


1
您可以省去swapped=true提前检查并根据阵列大小递减计数。请参阅我的20字节x86-16版本,该版本对8位整数进行排序。我可能会制作一个普通的32或64位x86版本,该版本在某个点上对32位整数进行排序,但是16位模式下的8位整数对于x86来说是一个不错的选择。
彼得·科德斯

4

Awk,66个字节

{b=$0;a[b]}m<b{m=b}n>b{n=b}END{for(i=n;i<=m;i++)if(i in a)print i}

awk中的数组就像字典,而不是C数组。索引可以是不连续的,并且可以根据需要增长(并创建)。因此,我们a为输入创建一个数组,每一行都是一个键。然后保存最小值和最大值。然后,我们从min到max循环,并打印中存在的所有键ab只是为了避免重复使用$0


4

Python 3,91 62 47字节

def f(z):
 while z:m=min(z);z.remove(m);yield m

感谢wnnmawSeeq提供高尔夫帮助。

参数z应为列表。这是选择排序的一种变体。

我不确定如何minbuilt-in sorting functionsPython相提并论,因为我不确定Python如何实现min。希望这种解决方案仍然可以。欢迎在评论中或PPCG聊天中提出任何高尔夫建议。


确保说明您使用的是哪种类型的排序。
Michelfrancis Bustillos

@MichelfrancisBustillos我真的忘记了这是什么算法。可能是选择排序吗?
Sherlock16年

1
出于好奇,为什么不直接列出清单呢?该问题允许使用开放输入格式
wnnmaw '16

1
@wnnmaw Dang,我写了一篇,却忘了发帖了。感谢您的提醒:D
Sherlock9

嗯,也许def f(z):\nwhile z:m=min(z);z.remove(m);yield m
Seequ 2016年

4

MATL,11个字节

`t4#X<2#)tn

在线尝试!

通过以下过程进行排序,即On 2):

  1. 取数组的最小值。
  2. 从数组中删除该值,并将其存储以供后续显示。
  3. 对数组的其余部分应用相同的过程,直到它变空。
  4. 按获得顺序显示所有数字。

MATL是基于堆栈的。剩余值的数组保留在堆栈的顶部。删除的值按顺序在下面。在程序结束时,将显示所有这些值。顶部的数组也将显示,但由于为空,因此未显示。

`        % Do...while loop
  t      %   Duplicate. Implicitly take input in the first iteration
  4#X<   %   Compute index of mininum of the array
  2#)    %   Push the minimum, and then the array with remaining entries
  tn     %   Duplicate and push number of elements, to be used as loop condition
         % Implicitly end do...while loop
         % Implicitly display stack contents


3

严重的是6个字节

,;l@╨m

在线尝试!

这与许多其他答案具有相同的作用:生成所有排列,选择最小值。我有点忘了在我尝试以下解决方案时这将起作用。

说明:

,;l@╨m
,;l@    push len(input), input
    ╨m  minimum permutation

严重地,25个字节(非竞争)

如果不是我刚刚修复的shuffle命令中的错误,这将很有竞争力。

,1WX╚;;pX@dXZ`i@-0<`MπYWX

在线尝试! 这实现了有史以来最好的排序算法:Bogosort

说明:

,1WX╚;;pX@dXZ`i@-0<`MπYWX
,                          get input
 1W                    WX  do-while:
   X                         discard
    ╚                        shuffle
     ;;                      dupe twice
       pX@dX                 remove first element of first dupe and last element of second dupe
            Z                zip
             `i@-0<`MπY      test if all differences are positive (if any are not, the list is not sorted), negate (1 if not sorted else 0)

3

MATL,17 16字节

@LuisMendo,节省了一个字节,创建了空数组

vTbtX<-QI$(f8M+q

桶排序。不要尝试使用大于2 31 -1 的范围。

在线尝试!

说明

v                  % push an empty array
 T                 % push 1
  b                % bubble the input array up to the top of the stack
   t               % duplicate it
    X<             % find the minimum
      -            % subtract min from input array
       Q           % and increment to adjust for 1-based indexing
        I$(        % resulting array used as indices of empty array 
                   % (the [] way up at the top) that are assigned 1 (from T)
           f       % find the nonzero indices
            8M     % magically retrieve the 4th previous function input :/
                     (aka, the min input array value)
              +    % add it to the indices
               q   % and decrement

瓷砖:

  • 您可以使用MATL在MATL中初始化一个空数组[]并对其进行增长,就像在MATLAB中一样
  • 如何(用于分配索引
  • 如何使用M自动剪贴板

新的一天,新的TIL:

  • vertcat 当堆栈上没有要连接的内容时,会神奇地创建一个空数组

添加到您的TIL:可以将首字母 []替换为v。这是因为输入的默认数量v是堆栈中元素的数量
Luis Mendo

@LuisMendo Sooo ...如果堆栈上只有一个数组...?正在调查。
烧杯

然后它什么也不做。可以将其视为vertcat(STACK{:})
Luis Mendo


3

R,68字节

接受输入i和输出o,这是已排序的列表。

o<-i
for(j in 1:length(i)){
x<-(i-min(i))==0
o[j]<-i[x]
i<-i[!x]
}
o

说明:

o<-i                      # Defines output as o
 for(j in 1:length(i)){   # Initializes loop for length of input
  x<-(i-min(i))==0        # Generates logical vector by finding the value 0 
                          # of input less the minimum of input. 
   o[j]<-i[x]             # Puts the smallest value at position j
    i<-i[!x]              # Removes the smallest value from input
      }                   # Ends loop
       o                  # Returns sorted list

避免排列意味着它可以相对快速地对大型列表进行排序。“技巧”是,从输入中减去最小值会留下一个确定最小值和最小值位置的单个0。


3

Java 8,112 92字节

这是另一种选择。输入是List t整数a ,将排序后的输出打印到标准输出中。

t->{for(;0<t.size();System.out.println(t.remove(t.indexOf(java.util.Collections.min(t)))));}

更新资料

  • -20 [16-08-21]使用了lambda

大家好,非线性,欢迎来到PPCG!
isaacg '16

欢迎来到编程难题和代码高尔夫球!看来您的代码假定t存在一个变量,这使其成为摘要;我们要求提交的内容必须是使用我们默认I / O格式的完整程序或功能。我们还需要导入以将字节数考虑在内。如果您有任何疑问,请告诉我!
Alex A.

感谢您的资源!我将答案修改为函数并包含导入。
NonlinearFruit16年

2

视网膜,95岁

修改后的冒泡排序。我怀疑即使没有内置视网膜排序,也有更好的方法可以做到这一点。

-\d+
$*n
\d+
$*11
+`(1+) (n+)
$2 $1
+`\b(n+) (\1n+)|(1+)(1+) \3\b
$2$3 $1$3$4
1(1*)
$.1
n+
-$.&
  • 第1阶段-将-ve整数转换为带有n数字的一元;放下-迹象。
  • 第2阶段-将+ ve和零整数转换1为以数字为一元数;添加1到每一个,从而使零由下式表示1
  • 第3阶段-将所有-ves移到最前面。
  • 阶段4-排序:将具有最大幅度(即最小数值)的所有-ves移到更高的-ves之前。将较小的+ ves移至较大的+ ves。
  • 阶段5-从中删除1,并将+ ve一元转换为十进制。
  • 阶段6-将-ve一元转换为十进制,包括符号。

在线尝试。



@LeakyNun不会对列表中的最后一个元素进行排序。
mbomb007 '17

@ mbomb007对,没关系。
Leaky Nun

2

Ruby,22个字节

一个快速的排列排序。在O(n!)空间和时间中运行。

->a{a.permutation.min}

2

Clojure,73个 35字节

Bogosort :)

#(if(apply < %)%(recur(shuffle %)))

早期版本:

#(reduce(fn[r i](let[[a b](split-with(partial > i)r)](concat a[i]b)))[]%)

r通过将其分为“小于i”和“大于i”两部分来简化为排序列表。我猜这是插入排序


真好!我不知道您可以recur使用匿名函数。还不知道shuffle
Matias Bjarland '18

2

Ruby,26个 24字节

选择排序,类似于Value Ink的答案,但是使用了不同的方法来提高高尔夫球感。

根据规范:“输入/输出可以用您选择的任何方法完成,只要它是人类可读的”。我认为这符合描述,输出是具有单个元素的数组的数组。

->l{l.map{l-l-=[l.min]}}

例:

->l{l.map{l-l-=[l.min]}}[[2,4,3,1]]
=> [[1], [2], [3], [4]]

2

Java 7中,106个 104字节

void a(int[]a){for(int b=a.length-1,d=0,c=0,e;d<b*b;c=++d%b)if(a[c]>a[c+1]){e=a[c];a[c++]=a[c];a[c]=e;}}

这是一个很好的泡泡。函数参数已就地修改,因此我不必返回任何内容。仍然试图从中挤出一些字节,这样我就可以击败有人发布的Java lambda。

-1字节感谢Geobits指出正常交换胜于异或
-1字节感谢Leaky Nun指出我可以将所有int声明移入for循环

在线尝试!


2

Ruby,22个字节

->a{[*a.min..a.max]&a}

在输入数组的最小和最大元素之间的范围之外构建一个数组。返回两个数组之间的交集。



@PeterCordes这就是重点
dkudriavtsev

这个问题要求您描述它的种类,因此我认为链接到众所周知的算法以及仅描述其实际作用是很有用的。
彼得·科德斯

真正。感谢@PeterCordes
dkudriavtsev
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.