首先对奇数进行排序


20

重新排列给定列表,使所有奇数出现在所有偶数之前。除此要求外,输出列表可以按任何顺序排列。

输入将仅包含整数,但它们可以为负数,并且可以重复,并且可以按任何顺序出现。

最短的解决方案获胜。

测试用例

[1,2][1,2]

[2,1][1,2]

[1,0,0][1,0,0]

[0,0,-1][-1,0,0]

[3,4,3][3,3,4]

[-4,3,3][3,3,-4]

[2,2,2,3][3,2,2,2]

[3,2,2,2,1,2][1,3,2,2,2,2][3,1,2,2,2,2]

[-2,-2,-2,-1,-2,-3][-1,-3,-2,-2,-2,-2,][-3,-1,-2,-2,-2,-2,]

[][]


泰 好问题。答:奇数可以任何顺序出现。:)
display_name

11
即使挑战很简单,添加一些测试用例也很好。例如,乍一看,我认为奇数和偶数块也需要排序。
Laikoni

1
@AsoneTuhid是:),数字可以重复。
display_name

11
@Willmore您永远不会对代码高尔夫一无所知,规则很重要。在发布之前,请下次使用沙盒来澄清您的问题。
Asone Tuhid

12
请编辑您的问题,以包括您在评论中所作的澄清。
Laikoni

Answers:






9

C ++,79 76 64字节

[](auto a,auto b){while(a<--b)*a%2?*++a:(*a^=*b,*b^=*a,*a^=*b);}

此函数接受一对迭代器(必须是随机访问迭代器),并将它们稳定地移向彼此。当a指向奇数时,它会前进。否则,a指向偶数。b递减并iter_swap与一起使用a。(我们使用XOR交换,这使我们不必包含<algorithm>-或<utility>for std::swap)。

b指向偶数时,有不必要的交换,但是我们在打高尔夫球,而不是提高效率!

演示版

auto f=[](auto a,auto b){while(a<--b)*a%2?*++a:(*a^=*b,*b^=*a,*a^=*b);};

#include <array>
#include <iostream>
int main()
{
    auto a = std::array{ 3,2,2,5,2,1,2 };

    f(a.begin(),a.end());

    for (auto i: a)
        std::cout << i << " ";
    std::cout << std::endl;
}

非竞争性答案

自然的C ++方法是std::partition,但它的大小为83个字节:

#include<algorithm>
[](auto a,auto b){std::partition(a,b,[](auto x){return x&1;});}

我相信这是80个字节,因为在#include指令之后您需要换行符。我的数学虽然糟透了^^。您可以替换!=-,节省1个字节。我喜欢您的方法,这很聪明!
OOBalance

1
否则,迭代器可能彼此传递而不会变得相等。 如果您使用的是RandomAccessIterator,那么使用while(a<b)它比a!=b使用@OOBalance的a-b版本更方便。
彼得·科德斯

您可以替换algorithmregexcodegolf.stackexchange.com/a/150895
OOBalance '18


7

Perl 6、12个字节

*.sort(*%%2)

在线尝试!

某些按奇偶校验对输入进行排序的Whatever代码,首先使用奇数。您可以删除%以获得第一个偶数。请注意,“任何”都是这种匿名函数的名称。


1
抱歉! 我不小心编辑了您的答案,而不是我的!
查斯·布朗



5

Stax,5个字节

{|eom

运行并调试

说明:

{|eom Full program, implicit input
{  o  Sort by key:
 |e     Is odd?
    m Map over result:
        Implicit output with newline

5

Haskell23 22字节

f odd<>f even
f=filter

在线尝试!这相当于

g x = filter odd x ++ filter even x

-1字节感谢Lynn


其他方法:

(<>).($odd)<*>($even)$filter
f x=[i|m<-[0,1],i<-x,odd$m+i]
f x=[i|m<-[1,0],i<-x,mod i 2==m]
f x=id=<<filter<$>[odd,even]<*>[x]

但这不是需要import Data.Semigroup吗?
AlexJ136

1
从GHC 8.4.1开始,@ AlexJ136 (<>)是Prelude的一部分。由于TIO仍运行较旧的版本,因此需要在此处导入。但是您是对的,我应该直接提到这一点。
Laikoni '18

1
k odd<>k even;k=filter保存一个字节。
林恩


5

JavaScript(Node.js),29字节

a=>a.sort((a,b)=>(b&1)-(a&1))

在线尝试!通过仅支持正值来节省4个字节b%2-a%2。如果您这样写:

function(a){return a.sort((a,b)=>(b&1)-(a&1))}

那么它将适用于各种不稳定排序的旧JavaScript实现。


1
不行a=>a.sort((a,b)=>b&1-a&1)吗?
亚历克西斯·福克斯

1
@AlexisFacques不,解析为b&(1-a)&1
尼尔

1
a=>a.sort(a=>++a&1)短:)
马克斯

@Max可以在给定的测试用例上工作,但是如果有人找到了一个不起作用的示例,我不会感到惊讶。
尼尔,

1
@Max您最好将其作为自己的答案提交。
尼尔,

5

T-SQL,26个字节

SELECT*FROM t ORDER BY~i&1

使用按位AND运算符“&”将最后一位与1进行比较。

编辑:按位不小于添加1。编辑2:重新排序以允许删除空间。


1
真好!击败我5!通过交换顺序和删除空格来节省一个字节:ORDER BY~i&1
BradC

4

果冻,3 个字节

ḂÞṚ

在线尝试!

我更希望的原子之一似乎是一个偶数(将使这2个字节),如果没有它,我们必须将其反转。

ḂÞṚ - Link: list of integers
 Þ  - sort by:
Ḃ   -   bit (least significant bit - i.e. 1 if odd 0 if even)
  Ṛ - reverse

4

JavaScript,22 20字节

a=>a.sort(a=>!(a%2))

在线尝试!


我认为您可以在第三个括号内加上括号a
乔纳森·弗雷希

如果0包含在数组中则不起作用。
毛茸茸的

错了 js比较器无法以这种方式工作。developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/…–
Qwertiy,

2
根据ECMA规范,“如果comparefn不是未定义的,并且不是此数组元素的一致比较函数(请参见下文),则sort的行为是实现定义的。” 此比较功能不一致。因此,这不是JavaScript的答案,但可能是某些特定JavaScript实现的答案,您必须命名哪种实现。
user5090812

1
我认为这失败了[1,2,3,4,5,6,6,-1,-2,-3,-4]。JavaScript array.sort很奇怪。
Chas Brown

4

PHP,55字节

大约14个月后,我现在在打高尔夫球方面变得更好一些:

for(;''<$n=$argv[++$i];$s=$n%2?"$n $s":"$s $n");echo$s;

在线尝试!


PHP(> = 5.4),84 82字节

(-2个字节,感谢Ismael Miguel

<?array_shift($a=&$argv);usort($a,function($i){return$i%2==0;});echo join(' ',$a);

要运行它:

php -n <filename> <number_1> <number_2> ... <number_n>

例:

php -n sort_odds_first.php 2 0 1 -1 3 8 29 -666

在线尝试!


1
代替$a=array_slice($argv,1);,使用array_shift($a=&$argv);,它可以节省1个字节。此外,之前删除的空间$ajoin(' ', $a),节省了一个字节。另外,PHP 5.3给出了不同的结果。您应指定此解决方案适用于哪个PHP版本。
伊斯梅尔·米格尔

1
@IsmaelMiguel:感谢您的 array_shift想法并指出了空间错误。我不确定我怎么会错过空格:DI也在标题中添加了PHP> = 5.4。
夜间2

这是一个常见的错误。array_shift当我尝试并工作时,我实际上感到惊讶。
伊斯梅尔·米格尔


3

外壳,4个字节

↔Ö%2

在线尝试!

说明

 Ö     sort input according to the result of the following function
  %2   modulo 2
↔      reverse result to get odd numbers to the front


3

C#,23个字节

i=>i.OrderBy(u=>u%2==0)

确实非常向前:这基本上将数字转换为布尔值,而true意味着数字是偶数且false是奇数。因为true高于false偶数,第一个出现。

格式化的版本如下所示:

i => i.OrderBy (u => u % 2 == 0)

您可以像这样测试它:

Console.WriteLine (string.Join (",", new Func <IEnumerable <int>, IEnumerable <int>> (
                                    i => i.OrderBy (u => u % 2 == 0)
                                ).Invoke (new [] {3, 2, 2, 2, 1, 2, 5, 5})));

结果如下:

3,1,5,5,2,2,2,2




3

JavaScript(Chrome v67)-24 19 23字节

a=>a.sort(a=>!(a&1)-.5)

@的使用&1而不是Math.abs()%2被@Neil窃取。谢谢!

感谢@Shaggy显示我的hacky 19字节解决方案无效。如果有人愿意:

取决于浏览器如何处理hacky返回值0。Chrome v67,经过100000次随机数组迭代后,再也没有对它进行错误排序。我坚信它可以正常工作-我相信它也依赖于Chrome使用的特定排序算法。(它可能在其他浏览器中有效,这不是重点)

a=>a.sort(a=>++a&1)


欢迎使用PPCG :) [-5,-4,-3,-2,-1,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19]在我的Chrome 67控制台中输入失败,输出[7,-5,-3,17,-1,15,1,13,3,11,5,9,2,19,14,-4,6,18,-2,16,0,10,8,12,4]
毛茸茸的

@Shaggy-哎呀!你是绝对正确的!
最多


3

PowerShell的22 19字节

$args|sort{!($_%2)}

在线尝试!

通过展开输入,例如 $a=(3,4,3); .\sort-odd-numbers-first.ps1 @a在TIO上显示为每个条目的单独参数。

像这里的其他答案一样,Sort-Object可以基于表达式进行比较。这里的表达式是!($_%2),即赔率被排序为$false,偶数被排序为$true。由于比较布尔值的方式,错误值首先被排序。这会将赔率移至输出的开头,将偶数移至输出的结尾。Sort-Object是稳定的,因此各个项目在其各自类别中的排序不会改变(如TIO示例中所示)。

-3个字节,感谢mazzy。


它可以使用splatting。例如$a=(3,4,3); .\sort-odd-numbers-first.ps1 @a。这样$args|sort{!($_%2)}就足够了。是不是
mazzy

为什么要“作弊”?它是本机的Powershell功能。另一个问题:我们可以在codeGolf解决方案中使用splatting吗?例如,一个解决方案包含多个功能。如果可以的话,为什么不应该外部呼叫呢?如果我们不能,那么为什么禁止该功能?以及哪些功能也被禁止?
mazzy

1
@mazzy感谢您指出这一点。我已经更新了我的提交。
AdmBorkBork

3

红宝石,23个字节

->a{a.sort_by{|i|~i%2}}

在线尝试!

说明:

sort_by对每个数字进行排序,就好像其值是块(~i%2)的结果

~x等价于-x-1并优先于%2

奇数将等于0,偶数将等于1因此奇数将首先被排序。

几乎不相关:这适用于Homebrew 2.5.1p57中的ruby(因为它基于一个小错误),但仅适用于20字节的非负整数

->a{a.sort{|i|i%-2}}

说明:

这使用sort了期望一个带有2个值并返回的块-10或者1取决于第一个值是否更大,它们相等还是第二个值更大。

此处给出的块将忽略第二个值,-1如果第一个数字为奇数或0偶数时返回。

它不能保证能正常工作,但可以在某些(我认为是错误的)实现中实现。


我们通过此处的实现定义语言,因此您的20字节解决方案有效。
毛茸茸的

@Shaggy没关系,我昨天搞砸了我的测试。
Asone Tuhid

3

6502机器代码例程,47字节

A0 00 84 FE B1 FB 4A 90 07 C8 C4 FD F0 20 D0 F4 2A 85 02 84 FE A4 FD 88 C4 FE
F0 12 B1 FB 4A 90 F6 2A AA A5 02 91 FB A4 FE 8A 91 FB 90 D6 60

期望在$fb/中指向数字数组的指针,$fc并在其中指向该数组的长度$fd。操纵数组以使所有奇数都在前面。这是与位置无关的代码,因此不需要加载地址。

由于6502是8位芯片(因此指令仅处理8位值,可以选择带符号),因此有效数字范围为[-128 .. 127],最大数组大小为256

评论拆解

; function to "partially sort" array, so all odd numbers come before all
; even numbers.
;
; input:
;   $fb/$fc: address of array to sort
;   $fd:     length of array to sort, 0 means 256 (maximum size)
;
; clobbers:
;   $fd/$fe: position from back/front of array
;   $2:      temporary for exchanging two values
;   A, X, Y

 .oddfirst:
A0 00       LDY #$00            ; initialize index from front
84 FE       STY $FE             ; to 0

 .search_front:
B1 FB       LDA ($FB),Y         ; load number from front
4A          LSR A               ; check for even/odd by shifting
90 07       BCC .search_back    ; if odd -> to searching from back
C8          INY                 ; next position from front
C4 FD       CPY $FD             ; same as position searching from back?
F0 20       BEQ .done           ; then we're finished
D0 F4       BNE .search_front   ; else check next from front
 .search_back:
2A          ROL A               ; shift carry back in
85 02       STA $02             ; and save number to temp
84 FE       STY $FE             ; save index from front
A4 FD       LDY $FD             ; load index from back
 .sb_loop:
88          DEY                 ; previous position from back
C4 FE       CPY $FE             ; same as position searching from front?
F0 12       BEQ .done           ; then we're finished
B1 FB       LDA ($FB),Y         ; load number from back
4A          LSR A               ; check for even/odd by shifting
90 F6       BCC .sb_loop        ; if odd -> check previous position
2A          ROL A               ; shift carry back in
AA          TAX                 ; remember in X
A5 02       LDA $02             ; load temporary from front
91 FB       STA ($FB),Y         ; store at current position
A4 FE       LDY $FE             ; load index from front
8A          TXA                 ; load remembered number
91 FB       STA ($FB),Y         ; store at current position
90 D6       BCC .search_front   ; and back to searching from front
 .done:
60          RTS

使用例程的示例C64汇编程序:

在线演示

屏幕截图

ca65语法中的代码:

.import oddfirst ; link with routine above

.segment "BHDR" ; BASIC header
                .word   $0801           ; load address
                .word   $080b           ; pointer next BASIC line
                .word   2018            ; line number
                .byte   $9e             ; BASIC token "SYS"
                .byte   "2061",$0,$0,$0 ; 2061 ($080d) and terminating 0 bytes

.bss
linebuf:        .res    5               ; maximum length of a valid signed
                                        ; 8-bit number input
convbuf:        .res    3               ; 3 BCD digits for signed 8-bit
                                        ; number conversion
numbers:        .res    $100            ; maximum array size that can be
                                        ; directly handled with indexing
                                        ; instructions

.data
prompt:         .byte   "> ", $0
message:        .byte   $d, $d, "Enter one number per line.", $d
                .byte   "just press enter (empty line) when done.", $0
errmsg:         .byte   "Error parsing number, try again.", $d, $0

.code
                lda     #$17            ; set upper/lower mode
                sta     $d018

                lda     #0
                sta     $2a             ; index for number array
                sta     $52             ; flag that at least one number was
                                        ; entered

                lda     #<message       ; display message
                ldy     #>message
                jsr     $ab1e

inputloop:
                lda     #<prompt        ; display prompt
                ldy     #>prompt
                jsr     $ab1e

                lda     #<linebuf       ; read string into buffer
                ldy     #>linebuf
                ldx     #5
                jsr     readline

                lda     linebuf         ; empty line?
                beq     process         ; -> start processing

                lda     #<linebuf       ; convert input to int8
                ldy     #>linebuf
                jsr     toint8
                bcc     numok           ; successful -> store number
                lda     #<errmsg        ; else show error message and repeat
                ldy     #>errmsg
                jsr     $ab1e
                bcs     inputloop

numok:          ldx     #$ff            ; set flag that we have a number
                stx     $52
                ldx     $2a
                sta     numbers,x
                inc     $2a             ; next index
                bne     inputloop       ; if array not full, next input

process:        lda     $52             ; check we have some numbers
                beq     exit            ; otherwise exit program

                lda     #<numbers       ; address of array to $fb/fc
                sta     $fb
                lda     #>numbers
                sta     $fc
                lda     $2a             ; length of array to $fd
                sta     $fd
                jsr     oddfirst        ; call "sorting" function

                lda     #$0             ; index variable for output loop
                sta     $52
outloop:        ldy     $52             ; load current index
                lda     numbers,y       ; load current number
                jsr     printnum        ; -> output
                inc     $52             ; next index
                lda     $52             ; compare with ...
                cmp     $2a             ; ... array size
                bne     outloop         ; not reached yet -> repeat

exit:           rts                     ; done, exit program

; read a line of input from keyboard, terminate it with 0
; expects pointer to input buffer in A/Y, buffer length in X
.proc readline
                dex
                stx     $fb
                sta     $fc
                sty     $fd
                ldy     #$0
                sty     $cc             ; enable cursor blinking
                sty     $fe             ; temporary for loop variable
getkey:         jsr     $f142           ; get character from keyboard
                beq     getkey
                sta     $2              ; save to temporary
                and     #$7f
                cmp     #$20            ; check for control character
                bcs     checkout        ; no -> check buffer size
                cmp     #$d             ; was it enter/return?
                beq     prepout         ; -> normal flow
                cmp     #$14            ; was it backspace/delete?
                bne     getkey          ; if not, get next char
                lda     $fe             ; check current index
                beq     getkey          ; zero -> backspace not possible
                bne     prepout         ; skip checking buffer size for bs
checkout:       lda     $fe             ; buffer index
                cmp     $fb             ; check against buffer size
                beq     getkey          ; if it would overflow, loop again
prepout:        sei                     ; no interrupts
                ldy     $d3             ; get current screen column
                lda     ($d1),y         ; and clear 
                and     #$7f            ;   cursor in
                sta     ($d1),y         ;   current row
output:         lda     $2              ; load character
                jsr     $e716           ;   and output
                ldx     $cf             ; check cursor phase
                beq     store           ; invisible -> to store
                ldy     $d3             ; get current screen column
                lda     ($d1),y         ; and show
                ora     #$80            ;   cursor in
                sta     ($d1),y         ;   current row
                lda     $2              ; load character
store:          cli                     ; enable interrupts
                cmp     #$14            ; was it backspace/delete?
                beq     backspace       ; to backspace handling code
                cmp     #$d             ; was it enter/return?
                beq     done            ; then we're done.
                ldy     $fe             ; load buffer index
                sta     ($fc),y         ; store character in buffer
                iny                     ; advance buffer index
                sty     $fe
                bne     getkey          ; not zero -> ok
done:           lda     #$0             ; terminate string in buffer with zero
                ldy     $fe             ; get buffer index
                sta     ($fc),y         ; store terminator in buffer
                sei                     ; no interrupts
                ldy     $d3             ; get current screen column
                lda     ($d1),y         ; and clear 
                and     #$7f            ;   cursor in
                sta     ($d1),y         ;   current row
                inc     $cc             ; disable cursor blinking
                cli                     ; enable interrupts
                rts                     ; return
backspace:      dec     $fe             ; decrement buffer index
                bcs     getkey          ; and get next key
.endproc

; print an int8 number to the screen
; input:
;   A - the number to print
; clobbers:
;   X, Y
.proc printnum
                bpl     doprint         ; positive? -> direct number output
                eor     #$ff            ; else invert, 
                sta     $2              ; ...
                inc     $2              ; add one,
                lda     #'-'            ; output a minus sign
                jsr     $e716
                lda     $2
doprint:        tax                     ; number to X reg
                lda     #$0             ; set A to 0
                jsr     $bdcd           ; routine for uint16 in X/A output
                lda     #' '            
                jmp     $e716           ; and print a space
.endproc

; parse / convert int8 number using a BCD representation and double-dabble,
; handle negative numbers.
.proc toint8
                sta     $fb
                sty     $fc
                ldy     #$0
                sty     $fd
                sty     $fe
                sty     convbuf
                sty     convbuf+1
                sty     convbuf+2
scanloop:       lda     ($fb),y
                beq     copy
                iny
                cmp     #$20
                beq     scanloop
                cmp     #$2d
                beq     minus
                cmp     #$30
                bcc     error
                cmp     #$3a
                bcs     error
                inc     $fd
                bcc     scanloop
minus:          lda     $fd
                bne     error
                lda     $fe
                bne     error
                inc     $fe
                bne     scanloop
error:          sec
                rts
copy:           dey
                bmi     error
                ldx     #$2
copyloop:       lda     ($fb),y
                cmp     #$30
                bcc     copynext
                cmp     #$3a
                bcs     copynext
                sec
                sbc     #$30
                sta     convbuf,x
                dex
copynext:       dey
                bpl     copyloop
                lda     #$0
                sta     $fb
                ldx     #$8
loop:           lsr     convbuf
                lda     convbuf+1
                bcc     skipbit1
                ora     #$10
skipbit1:       lsr     a
                sta     convbuf+1
                lda     convbuf+2
                bcc     skipbit2
                ora     #$10
skipbit2:       lsr     a
                sta     convbuf+2
                ror     $fb
                dex
                beq     done
                lda     convbuf
                cmp     #$8
                bmi     nosub1
                sbc     #$3
                sta     convbuf
nosub1:         lda     convbuf+1
                cmp     #$8
                bmi     nosub2
                sbc     #$3
                sta     convbuf+1
nosub2:         lda     convbuf+2
                cmp     #$8
                bmi     loop
                sbc     #$3
                sta     convbuf+2
                bcs     loop
done:           lda     $fe
                beq     positive
                lda     #$ff
                eor     $fb
                sta     $fb
                inc     $fb
positive:       lda     $fb
                clc
                rts
.endproc


2

Clojure-35个字节

(defn o[c](sort(fn[p _](odd? p))c))

取消高尔夫:

(defn oddsort [col]
  (sort (fn [p _] (odd? p)) col))

有很多改进的空间,例如,您可以通过提交匿名函数,该函数的创建语法较短#(...)sort-by尽管提交已经存在,但是您也可以尝试一下。
NikoNyrh

@NikoNyrh:尝试了一个#()匿名函数,但由于传递了两个参数,但仅在预期/使用的情况下出现了Arity 错误,并且引入%2了更多字符。有兴趣了解如何做到这一点。
鲍勃·贾维斯
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.