代码高尔夫:排列


21

编写一个函数,该函数接受一组整数(可以是列表,数组或任何其他具有不同数字的容器)作为输入,并输出所有其排列的列表。

Python(95个字符):

p=lambda s:s and sum(map(lambda e:map(lambda p:[e]+p,p(filter(lambda x:x!=e,s))),s),[]) or [[]]

用相同的语言击败真是太好了,但是其他语言的实现实在值得欢迎!

Answers:


10

Python-76个字符

比g子手更长,但从头开始实现。

p=lambda x:x and[[a]+b for a in x for b in p([c for c in x if c!=a])]or[[]]

我喜欢这里理解的用法。它确实简化了我发布的代码!
— zxul767'3


9

J,11个字符

(i.@!@#A.[)

用法:

   (i.@!@#A.[) 1 3 5
1 3 5
1 5 3
3 1 5
3 5 1
5 1 3
5 3 1

说明:

i.@!@# 使用三个动词返回从0到(!n)-1的列表,其中n是给定列表中的项数。

[返回列表本身。在给出的示例中0 1 2 3 4 5 A. 1 3 5。

A.返回第一个列表中每个项目的第二个列表的可能排列(种类-在此给出了适当的解释)。


提供指向有关J?的信息的链接。
— Sparr 2012年

1
@Sparr J网站上有一些很好的指南- 学习C语言的J和J知识 -以及一个涵盖词汇表的页面。
— Gareth 2012年

8

Python-55个字符

from itertools import*
p=lambda x:list(permutations(x))

不完全是我希望人们写的东西……但是了解Python在标准库中有这样的实用程序很有用。
— zxul767'3

4
@ zxul767:为什么要重新发明轮子?使用标准库将被证明是非常有效的...(在这种情况下,打高尔夫球时简明扼要的代码;-)
— ChristopheD

8

哈斯克尔,44 43

p[]=[[]]
p l=[e:r|e<-l,r<-p$filter(/=e)l]

本质上与ugoren的解决方案相同,但Haskell的列表理解能力更好!


当然也可以

30

import Data.List
p=permutations


更有效的方法,不需要相等比较:

92

import Data.List
p[]=[[]]
p l=(\(l,(e:r))->map(e:)$p(l++r))=<<(init$zip(inits l)(tails l))

作为结果,当列表中有重复的元素时,此选项也适用。


4
最好的部分是列表理解的44行haskell解决方案比仅使用标准库的python解决方案要短。
— monadic 2012年

p=Data.List.permutations。不过,这感觉就像在作弊。同样,Data.List.permutations不按字典顺序输出排列。
— 约翰·德沃夏克

1
您可以改写p[]=[[]]为基本情况,节省两个字节。
— 林恩

@毛里斯:对!我以某种方式假定该空列表根据定义将具有零排列,但是从0开始!= 1显然没有任何意义。有一个空的基本情况会更好。
— 停止转动逆时针

3

在Q中(48)

g:{$[x=1;y;raze .z.s[x-1;y]{x,/:y except x}\:y]}

用法示例:

q)g[3;1 2 3]
1 2 3
1 3 2
2 1 3
2 3 1
3 1 2
3 2 1

2

红宝石-23个字符

f=->x{p *x.permutation}

例如f[[1,2,3]] 输出this。

但是使用[].permutation感觉就像在作弊,所以:

红宝石-59个字符

f=->a{a.size<2?[a]:a.flat_map{|x|f[(a-x=[x])].map{|y|x+y}}}

经过测试

100.times.all?{arr=(1..99).to_a.sample(rand(5)); arr.permutation.to_a==f[arr]}
=> true

如果需要,您可以使用IdeOne这样的网站进行代码演示:ideone.com/crvtD
— Llama先生

1
为什么使用内置语言功能会作弊?
— 马克·托马斯

@Mark编写一个仅调用内置函数的函数可能不会欺骗,但也不会很有趣。例如:“编写对数组进行排序的函数”->f(array) { return array.sort(); }
— jsvnm

2

Python-58个字符

通过输入一个集合,比ugoren的略短:

p=lambda x:x and[[y]+l for y in x for l in p(x-{y})]or[[]]

2

C, 270 243 239个字符

#define S t=*a;*a=a[i];a[i]=t;
#define R o=p(n,r-1,a+1,o,r-2,0)
int*p(n,r,a,o,i,t)int*a,*o;{if(!r)for(;n;--n)*o++=*--a;else{R;for(;i;--i){S R;S}}return o;}
P(n,a)int*a;{int N=1,i=n;for(;i;N*=i--);return p(n,n,a,malloc(N*n*8),n-1,0)-N*n;}

函数P(n,a)返回一个指向n!的指针!一个排列的排列,一个接一个地排列在一起。


1
一些技巧:<malloc.h> isn't needed (ignore the warnings). sizeof n`为4(可移植性很好,但更短则更好)。使用额外的参数作为变量(例如p(n,a,N,i))。int*p(..)int*a,o;。使用全局变量代替参数和返回值通常会有所帮助。
— ugoren 2012年

@ugoren,感谢您的提示。到目前为止,我还没有看到如何使用全局变量剃除更多的字符。(嘿,该函数本身就是线程安全的!)
— Michael Radford 2012年


1

JS- 154 146个字符

function f(x){var a=[],m;(m=x.length)>1?f(x.slice(1)).map(function(y){for(l=m;l--;a.push(y.slice(0,l).concat(x[0],y.slice(l))));}):a=[x];return a}

测试:f([1,2,3,4,5]).map(function(a){return a.join('')}).join('\n')返回此值。


1

[R

由于我们正在谈论置换,因此让我在R中显示至少一个解决方案:

library(gtools);v=c(3,4,5);permutations(length(v),length(v),v)

1

Perl 188

没有库例程,没有递归

sub p{$l=(@_=sort split'',shift)-1;while(print@_){$k=$j=$l;--$k while($_[$k-1]cmp$_[$k])>=0;$k||last;--$j while($_[$k-1]cmp$_[$j])>=0;@_[$j,$k-1]=@_[$k-1,$j];@_[$k..$l]=reverse@_[$k..$l]}}

1

Scala 30:

def p(s:Seq[_])=s.permutations 

Scala 195,快捷,肮脏,没有库的排列:

def c(x:Int,t:List[_]):List[_]={val l=t.size
val o=x%l
if(l>1){val r=c(x/l,t.tail)
r.take(o):::(t.head::r.drop(o))}else
t}
def p(y:List[_])=(0 to(1 to y.size).product).foreach(z=>println(c(z,y)))

val y=List(0,1,2,3)
p(y)

Scala 293,完整的类型安全迭代器:

class P[A](val l:Seq[A])extends Iterator[Seq[A]]{
var c=0
val s=(1 to l.size).product
def g(c:Int,t:List[A]):List[A]={
val n=t.size
val o=c%n
if(n>1){val r=g(c/n,t.tail)
r.take(o):::(t.head::r.drop(o))
}else
t}
def hasNext=c!=s
def next={c+=1
g(c-1,l.toList)}
}
for(e<-new P("golf"))println(e)


1

Pyth,4个字节

L.pb

是的,Pyth是在发布所有挑战之后创建的。这仍然很酷。:D

现场演示。

从stdin读取要短一个字节:

.pQ

1

的JavaScript 143 136 134 123

function p(s,a="",c="",i,z=[]){a+=c,i=s.length
!i?z.push(a):0
for(;i--;s.splice(i,0,c))p(s,a,c=s.splice(i,1),0,z);return z}

var perms = p([1,2,3]);

document.getElementById('output').innerHTML = perms.join("\n");
<pre id="output"></pre>


我认为您可以通过执行以下操作获得8个字节:js function p(s,a="",c="",i,z=[]){ 而不是 js function p(s,a,c,i,z){if(!z)a=c="",z=[]
— ColdK

谢谢ColdK。它有效,现在缩短了8个字节。
— wolfhammer '18


0

Python,53个字节

from itertools import*;lambda x:list(permutations(x))

1
这基本上是另一个提交的答案的副本。我认为您是独立提出的(您打得更好),但是我认为值得指出重复的事物。


0

K(oK),3个字节

解

prm

在线尝试!

说明:

这是3个字节的内置快捷方式,用于以下内置 47字节的功能:

{[x]{[x]$[x;,/x ,''o'x ^/:x;,x]}@$[-8>@x;!x;x]}

...如果我们知道要获取一个int列表作为输入,则可以缩短为23个字节:

{$[x;,/x,''o'x^/:x;,x]} / golfed built in
{                     } / lambda function with implicit input x
 $[ ;             ;  ]  / if[condition;true;false]
   x                    / if x is not null...
             x^/:x      / x except (^) each-right (/:) x; create length-x combinations
           o'           / call self (o) with each of these
       x,''             / x concatenated with each-each of these results (this is kinda magic to me)
     ,/                 / flatten list
                    ,x  / otherwise enlist x (enlisted empty list)

0

公理,160字节

p(a)==(#a=0=>[[]];r:=[[a.1]];r:=delete(r,1);n:=#a;m:=factorial n;m>1.E7=>r;b:=permutations n;for j in 1..m repeat(x:=b.j;r:=concat([a.(x.i)for i in 1..n],r));r)

不打高尔夫球

--Permutation of a
pmt(a)==
     #a=0=>[[]]
     r:=[[a.1]]; r:=delete(r,1) -- r has the type List List typeof(a)
     n:=#a
     m:=factorial n
     m>1.E7=>r
     b:=permutations(n)         --one built in for permutation indices 
     for j in 1..m repeat
        x:=b.j
        r:=concat([a.(x.i) for i in 1..n],r)
     r

所有这些都调用一个库函数,该函数给出索引的置换(仅整数作为[1]的置换,[1,2]的置换,[1,2,3]的置换等)。因此,获取这些集合就足够了索引并建立列表;必须注意,这似乎对每个X类型的List都适用

(4) -> p([1,2,3])
   Compiling function p with type List PositiveInteger -> List List
      PositiveInteger
   (4)  [[1,2,3],[1,3,2],[3,1,2],[2,1,3],[2,3,1],[3,2,1]]
                                          Type: List List PositiveInteger
(5) -> p([x^2,y*x,y^2])
   Compiling function p with type List Polynomial Integer -> List List
      Polynomial Integer
   (5)
      2      2    2  2        2  2            2  2        2  2    2      2
   [[x ,x y,y ],[x ,y ,x y],[y ,x ,x y],[x y,x ,y ],[x y,y ,x ],[y ,x y,x ]]
                                       Type: List List Polynomial Integer
(6) -> p([sin(x),log(y)])
   Compiling function p with type List Expression Integer -> List List
      Expression Integer
   (6)  [[sin(x),log(y)],[log(y),sin(x)]]
                                       Type: List List Expression Integer
(7) -> m:=p("abc")::List List Character
   Compiling function p with type String -> Any
   (7)  [[a,b,c],[a,c,b],[c,a,b],[b,a,c],[b,c,a],[c,b,a]]
                                                Type: List List Character
(8) -> [concat(map(x+->x::String, m.j))  for j in 1..#m]
   (8)  ["abc","acb","cab","bac","bca","cba"]
                                                        Type: List String

您是否有指向Axiom解释器的链接?我希望将其添加到“ 在线试用”中!,它看起来像是一种有趣的语言。
— Caird coinheringaahing

0

Japt,1个字节

á

Japt口译员

这碰到了,没有Japt的答案,所以我想我会继续添加一个。á当应用于数组且不带任何参数时,它是“获取所有排列”的内置函数。-R解释器链接中使用的标志仅修改结果的打印方式。


0

APL(NARS),39个字符,78个字节

{1≥k←≢w←,⍵:⊂w⋄↑,/{w[⍵],¨q w[a∼⍵]}¨a←⍳k}

测试:

  q←{1≥k←≢w←,⍵:⊂w⋄↑,/{w[⍵],¨q w[a∼⍵]}¨a←⍳k}
  q 1 2 3
1 2 3  1 3 2  2 1 3  2 3 1  3 1 2  3 2 1 
  q 'abcd'
abcd abdc acbd acdb adbc adcb bacd badc bcad bcda bdac bdca cabd cadb cbad cbda cdab cdba dabc dacb dbac dbca dcab dcba 

0

05AB1E- 2 1字节s

œ

输入必须是数组/列表。

说明:

œ //Takes all the permutations of the elements in the top of the stack (the input is a list, so it would work)

感谢Outgolfer的Erik节省了一个字节


您可以将输入作为单个列表,而不必将其用换行符分隔。
— 暴民埃里克(Erik the Outgolfer)'18年

谢谢!我现在可以将其缩短为一个字节!
— MilkyWay90 '18
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.