ใครที่สูงที่สุด?


32

เด็ก ๆ ที่ไม่มีการแชร์ขนาดที่แน่นอนของพวกเขาทั้งสองคนจะเรียงกันเป็นระเบียบ แต่ละคนสามารถเปรียบเทียบความสูงกับเพื่อนบ้านของพวกเขาได้ทันที เมื่อครูตะโกน "ยกมือถ้าคุณสูงที่สุด" พวกเขาจะทำเช่นนั้นถ้าพวกเขาสูงกว่าเพื่อนบ้านทั้งคู่และพวกเขาก็ทำพร้อมกัน ถ้าเพียงยกมือขึ้นเขาจะชนะ หากมีมากกว่าหนึ่งมือยกพวกเขาทั้งหมดจะถูกกำจัดออกจากแถว (รักษาลำดับของเด็กที่เหลือ) และพวกเขาทำซ้ำขั้นตอน

เขียนโปรแกรมซึ่งใช้อาร์เรย์ของจำนวนเต็มที่แตกต่างกัน (คุณสามารถถือว่าพวกเขาเป็นบวกอย่างเคร่งครัด) และส่งออกผู้ชนะของเกมนี้ นี่คือรหัสกอล์ฟดังนั้นรหัสที่สั้นที่สุดชนะ

ตัวอย่าง (แสดงขั้นตอนกลาง):

5 3 9 8 7 → 3 8 7 → 8

1 2 9 4 → 9

9 3 8 7 4 12 5 → 3 7 4 5 → 3 4 → 4


ผู้นำปัจจุบัน:

  1. เยลลี่: 17 ไบต์ [โดยเดนนิส♦]
  2. MATL: 20 ไบต์ [โดย Luis Mendo]
  3. APL: 28 ไบต์ [voidhawk]
  4. k: 40 bytes [โดย Paul Kerrigan]

นอกจากนี้ยังมีการต่อสู้ของ Pythons ที่เกิดขึ้น ยังคงรอภาษากอล์ฟเพิ่มขึ้นเพื่อแสดง

ฉันยอมรับคำตอบของเดนนิส♦ - หากมีผู้ชนะใหม่ฉันจะอัปเดตตัวเลือก


2
ฟังดูเหมือนว่า "ใครจะสูงที่สุดหรืออาจจะไม่" - หากต้องการค้นหา "ผู้ที่สูงที่สุด" คุณจะต้องกำจัดสิ่งที่ทำให้มือของตนแย่ลง
Alnitak

4
ฉันวาดความคล้ายคลึงกับเกมของเด็ก ๆ ซึ่งมีคนคนหนึ่งตะโกนวลีที่เป็นลายเซ็นหลังจากนั้นชื่อเกม สนุกมากพอที่สูงที่สุดมีโอกาสน้อยที่จะชนะ Asymptotically จาก N! การเปลี่ยนลำดับเฉพาะใน 2 ^ กรณี (N-1) ที่เขาชนะ
orion

คำตอบ:


4

เยลลี่ขนาด 17 ไบต์

j@N»3\=x@ḟ@ḢṖ?µ¬¿

อินพุตเป็นสตริงจำนวนเต็มที่คั่นด้วยเครื่องหมายจุลภาค

ลองออนไลน์!

เครดิตไปที่ @Xanderhall, @Sherlock และ @ErikGolfer สำหรับการวางรากฐาน

มันทำงานอย่างไร

j@N»3\=x@ḟ@ḢṖ?µ¬¿ Main link: Argument: A (integer or list of integers)

               ¬¿ While the logical NOT of A (0 for a positive integer, a non-empty
                  array for a non-empty array) is truthy:
              µ     Execute the chain of links to the left.
  N                   Negative; multiply all integers in A by -1.
j@                    Join -A, separating by A. This prepends and appends a
                      negative to A and appends more integers that will be ignored.
   »3\                Compute the maxima of all overlapping slices of length 3.
      =               Compare the maxima with the elements of A, yielding 1 or 0.
       x@             Repeat the elements of A, 1 or 0 times.
                      This ignores Booleans without a counterpart in A.
            Ṗ?        If the popped result is truthy, i.e., if it has at least two
                      elements:
         ḟ@             Filter/remove those elements from A.
                      Else:
           Ḣ            Head; extract the (only) element of the return value.

10

JavaScript (ES6), 78 76 72 ไบต์

ขอบคุณ @ edc65 สำหรับ -4 ไบต์

f=a=>a.map((c,i)=>(p>c|c<a[i+1]?q:r).push(p=c),p=q=[],r=[])&&r[1]?f(q):r

รับอาร์เรย์จำนวนเต็มและส่งออกอาร์เรย์ที่มีเฉพาะผู้ชนะ

ตัวอย่างการทดสอบ

นี่คือความพยายามอื่น ๆ ไม่กี่การใช้.filterและการประกอบอาร์เรย์:

f=a=>(q=a.filter((c,i)=>p>(p=c)|c<a[i+1]||0*r.push(c),p=r=[]))&&r[1]?f(q):r
f=a=>(r=a.filter((c,i)=>p<(p=c)&c>~~a[i+1]||0*r.push(c),p=q=[]))[1]?f(q):r
f=a=>[for(c of(i=p=q=[],r=[],a))(p>c|c<a[++i]?q:r).push(p=c)]&&r[1]?f(q):r
f=a=>(q=[for(c of(i=p=r=[],a))if(p>(p=c)|c<a[++i]||0*r.push(c))c])&&r[1]?f(q):r

หรือสองครั้งสำหรับลูปยาวน่ากลัว:

a=>eval("for(r=[,1];r[1]&&(p=i=q=[],r=[]);a=q)for(c of a)(p>c|c<a[++i]?q:r).push(p=c));r")

คำอธิบาย

วิธีการทำงานนี้ค่อนข้างง่าย: สร้างอาเรย์ของคนที่ค่อนข้างสูง ( r) และอาเรย์ของคนที่ไม่ได้เป็น ( q) แล้วส่งกลับrถ้ามีเพียงรายการเดียว ถ้าไม่มันจะทำงานเองqและส่งคืนผลลัพธ์ของการนั้น


ตัวอย่างขนมอยู่ที่ไหน
Kritixi Lithos

@KritixiLithos เพิ่มแล้ว :-)
ETHproductions

"[1,2,5,8,9,12,3,4,10] เอาท์พุท: 5" ฉันคิดว่านี่ควรจะเป็นผลลัพธ์ 8 ไม่ใช่ 5 อันดับแรก 12 และ 10 ถูกกำจัดแล้ว 9 และ 4 จากนั้น 8 ชนะ .
orion

1
@ orion ฉันไม่ดีตัวอย่างไม่ได้แปลงอาร์กิวเมนต์เป็นตัวเลขก่อนที่จะส่งไปยังฟังก์ชั่น สิ่งนี้ได้รับการแก้ไขแล้ว
ETHproductions

คุณสามารถบันทึก 4 ไบต์ตัวอย่างตัวกรองของคุณโดยการเปลี่ยนและq rคุณหลีกเลี่ยง&&rและนิพจน์ตัวกรองกลายเป็นไบต์ที่สั้นลงเช่นกัน
Neil

8

MATL , 20 ไบต์

`tTYadZSd0<~&)nq}x2M

อินพุตเป็นเวกเตอร์คอลัมน์โดยใช้;เป็นตัวคั่น

ลองออนไลน์! หรือตรวจสอบกรณีทดสอบทั้งหมด

คำอธิบาย

นี่คือการดำเนินการตามขั้นตอนที่อธิบายไว้ในความท้าทายโดยตรง do... whileห่วงช่วยให้การลบองค์ประกอบเพียงคนเดียวจนกว่าได้ถูกลบออก; และนั่นคือผลลัพธ์

องค์ประกอบที่จะลบจะถูกตรวจพบโดยการแตกต่าง signum แล้วความแตกต่างอีกครั้ง ผู้ที่ให้ค่าลบเป็นคนที่จะลบ

`        % Do...while
  t      %   Duplicate. Takes input (implicit) the first time
  TYa    %   Append and prepend a zero
  d      %   Consecutive differences
  ZS     %   Signum
  d      %   Consecutive differences
  0<~    %   Logical mask of non-negative values: these should be kept
  &)     %   Split array into two: those that should kept, then those removed
  nq     %   Size minus 1. This is used as loop condition. The loop will exit
         %   if this is 0, that is, if only one element was removed
}        % Finally (i.e. execute at the end of the loop)
  x      %   Delete array of remaining elements
  2M     %   Push last element that was removed
         % End (implicit)
         % Display (implicit)

4

Python3, 265 260 248 243 203 121 117 112 111 ไบต์

def T(I):
 b=[0];q=[];J=b+I+b
 for i,x in enumerate(I):[q,b][J[i]<x>J[i+2]]+=x,
 return len(b)<3and b[1]or T(q)

ขอบคุณ @ZacharyT, @orion และ @mathmandan สำหรับการบันทึก5 45ไบต์จำนวนมาก!


2

Haskell, 85 ไบต์

import Data.List
f x=(#)=<<(x\\)$[b|a:b:c:_<-tails$0:x++[0],b<a||b<c]
[s]#_=s
_#i=f i

ตัวอย่างการใช้งาน: ->f [9,3,8,7,4,12,5]4

มันทำงานอย่างไร:

f x =                            -- main function with parameter x
         [b|                  ]  -- make a list of all b
            a:b:c:_              -- where b is the second element of all lists with
                                 -- at least 3 elements
             <- tails $ 0:x++[0] -- drawn from the tails of x with a 0 pre- and
                                 -- appended (tails [1,2,3] -> [1,2,3],[2,3],[3],[])
               ,b<a||b<c         -- and b is not greater than its neighbors
   (#)=<<(x\\)                   -- feed the list difference of x and that list
                                 -- and the list itself to the function #

[s]#_s                           -- if the list difference is a singleton list,
                                 -- return the element
_#i=f i                          -- else start over with the list of b's

ตัวแปร, 85 ไบต์เช่นกัน:

import Data.List
f x|n<-[b|a:b:c:_<-tails$0:x++[0],b<a||b<c]=last$f n:[s|[s]<-[x\\n]]

ผูกลิสต์ของb(ดูด้านบน) ไปที่ n และส่งคืนอิลิเมนต์sหากx\\nเป็นรายการซิงเกิลและf nอื่น ๆ


คุณสามารถกำจัดของการนำเข้าและบันทึก 3 f x|y@(_:z)<-x++[0]=(#)=<<(x\\)$[b|(a,b,c)<-zip3(0:y)y z,b<a||b<c]ไบต์ด้วย
Zgarb

@Zgarb: \\ ยังคงต้องการนำเข้า Btw, นอกจากนี้ยังสามารถถูกแทนที่ด้วยtails ...|a:b:c:_<-scanr(:)[]$0:x++[0],...
nimi

ใช่แล้วฉันไม่ได้ตระหนักถึงสิ่งนั้น
Zgarb

2

Mathematica, 107 108 ไบต์

(For[x=y=#,Length@y>1,x=DeleteCases[x,#|##&@@y],y=Intersection[Max@@@x~Split~Less,#&@@@Split[x,#>#2&]]];y)&

คำอธิบาย

แรกตั้งxและเท่ากับการป้อนข้อมูลy ห่วงต่อไปจนกว่าList คือรายการขององค์ประกอบที่ต่อเนื่องและเพิ่มขึ้นคือรายการขององค์ประกอบที่ต่อเนื่องและลดลง การจดรายการทั้งหมดในอดีตให้รายชื่อเด็กที่สูงกว่าเด็กไปทางขวา (พร้อมกับเด็กขวาสุด) การรับอาร์กิวเมนต์แรก ( ) ของรายการทั้งหมดในรายการหลังให้รายการเด็กที่สูงกว่าเด็กไปทางซ้าย (พร้อมกับเด็กซ้ายสุด) จุดตัดของสองคนนี้จะเป็นรายการเด็กที่ยกมือขึ้น ตั้งค่านี้เท่ากับ ลบออกจากองค์ประกอบใด ๆ ที่ตรงกับองค์ประกอบของ( เทียบเท่ากับLength@y==1x~Split~LessSplit[x,#>#2&]Max#&yx=DeleteCases[x,#|##&@@y]xy#|##&Alternatives) yเมื่อสิ้นสุดห่วงผลตอบแทน หากเอาต์พุตต้องเป็นจำนวนเต็ม (แทนที่จะเป็นรายการที่มีจำนวนเต็มเดียว) ให้ส่งคืน#&@@y(+4 ไบต์)

ขอบคุณ Martin Ender ที่ช่วยประหยัด 2 ไบต์และทำให้ฉันปฏิบัติตามกฎ เปิดให้คำแนะนำ


ฉันไม่คิดว่าจะ!Lessทำงานได้ตามที่คุณคาดหวังเพราะสิ่งนี้ไม่ได้ประเมินฟังก์ชั่น คุณอาจต้องใช้Greater(หรือ#>#2&) ที่นั่น คุณสามารถใช้x~Split~Lessเป็นครั้งแรกSplitแม้ว่าและ>สำหรับLengthเงื่อนไข
Martin Ender

1
สำหรับที่มีการประเมินClear@yระหว่างสายฟังก์ชั่นฉันกลัวที่ไม่ถูกต้อง คุณอาจจะต้องตั้งค่าด้วยตัวคุณเองขอบเขตมันได้ดีขึ้นหรือเปิดนี้เป็นโปรแกรมที่เต็มไปด้วยและInput Print
Martin Ender

1

Perl 6 , 111 ไบต์

{(@_,{(($/=(0,|@$_,0).rotor(3=>-2).classify({+so .[1]>.[0,2].all})){1}>1??$/{0}!!$/{1})».[1]}...*==1)[*-1][0]}

ขยาย:

{  # bare block lambda with implicit parameter list 「@_」

  (                                    # generate a sequence
    @_,                                # starting with the input

    {   # code block used to get the next value in the sequence
        # which has implicit parameter 「$_」

        (
          (


            $/ =   # store in 「$/」 for later use

            ( 0, |@$_, 0 )             # the input with 0s before and after
            .rotor( 3 => -2 )          # take 3 at a time, back up 2, repeat
            .classify({
              +                        # Numify the following:
              so                       # simplify the following Junction
              .[1] > .[ 0, 2 ].all     # is the middle larger than its neighbors
            })



          ){1}                         # look at the values where it is true
          > 1                          # is there more than 1?

        ??                             # if so
          $/{ 0 }                      # look at the false ones instead

        !!                             # otherwise
          $/{ 1 }                      # look at the true ones

      )».[1]                           # undo the transformation from 「.rotor」
    }

    ...                                # keep doing that until

    * == 1                             # there is only one value
  )\
  [ * - 1 ]                            # the last value of the sequence
  [ 0 ]                                # make it a singular value ( not a list )

}

1

Python 2, 100 98 ไบต์

def f(A):
 t=[0];l=[];a=b=0
 for c in A+[0]:[l,t][a<b>c]+=[b];a,b=b,c
 return t[-2]and f(l)or t[1]

ใช้ผลตอบแทนการลัดวงจรเช่นเดียวกับคำตอบของ Yodle (โดย Zachary T)


คุณสามารถลบได้อีก 3 ไบต์โดย: การใช้+=b,แทน+=[b](เครดิตถึง mathmandan), t=[0]ใช้tเพื่อเพิ่มAและจากนั้นเมื่อเราเริ่มด้วย 0 ในการtตรวจสอบt[-2]<1จะสั้นกว่าlen(t)<2และใช้t[1]เป็นผลลัพธ์ในกรณีนั้น
orion

return t[-2]and f(l)or t[1]บรรทัดสุดท้ายกลายเป็น
orion

0

Mathematica, 101 ไบต์

If[Equal@@(a=Position[Max/@Partition[#,3,1,{2,2},0]-#,0]),#[[Last@a]],#0@Fold[Drop@##&,#,Reverse@a]]&

ฟังก์ชั่นวนซ้ำแบบไม่มีชื่อจะบันทึกรายการตัวเลขเป็นอินพุตและส่งคืนรายการที่มีหมายเลขเดียว (ผู้ชนะ) เป็นเอาต์พุต

หลักของอัลกอริทึมคือMax/@Partition[#,3,1,{2,2},0]ซึ่งคำนวณอาร์เรย์ของ (the-max-of-me-and-my-neighbours) จากรายการอินพุต a=Position[...-#,0]จากนั้นลบรายการเดิมและส่งคืนตำแหน่งที่ 0 เหล่านี้เป็นเด็กเลี้ยงมือ

If[Equal@@a, #[[Last@a]], #0@Fold[Drop@##&,#,Reverse@a]]&สาขาขึ้นอยู่กับว่าองค์ประกอบทั้งหมดของaเท่ากันหรือไม่ (ในกรณีนี้พวกเขาจะเป็นเพียงถ้าaเป็นซิงเกิล); ถ้าเป็นเช่นนั้นเด็กคนนี้เป็นผู้ชนะและเราให้หมายเลขของเธอ ถ้าไม่เช่นนั้นเราจะเรียกใช้ฟังก์ชันนี้ซ้ำในรายการพร้อมกับองค์ประกอบทั้งหมดที่ตำแหน่งในการaลบออก



0

PHP, 131 ไบต์

$r=$a=$argv;for(;$r[1];$a=array_values(array_diff($a,$r))){$r=[];foreach($a as$i=>$x)if($x>$a[$i-1]&$x>$a[$i+1])$r[]=$x;}echo$r[0];

รับตัวเลขจากอาร์กิวเมนต์บรรทัดคำสั่ง ล้มเหลวหากชื่อไฟล์เริ่มต้นด้วยจำนวนบวก

ทำให้พังถล่ม

// import (and init $r[1])
$r=$a=$argv;
// while more than 1 raised hand, remove them from data
for(;$r[1];$a=array_values(array_diff($a,$r)))
{
    // reset hands
    $r=[];
    // raise hands
    foreach($a as$i=>$x)
        if($x>$a[$i-1]&$x>$a[$i+1])$r[]=$x;
}
// output
echo$r[0];

0

k, 40 ไบต์

{$[1=+/B:(|>':|x)&>':x;x@&B;.z.s x@&~B]}

คำอธิบาย:
$ เป็น if-else

เงื่อนไขคือ 1 คือผลรวมของ B ซึ่งกำหนดเป็นขั้นต่ำของสองรายการที่สร้างขึ้นโดยการตรวจสอบว่า x สูงกว่าตำแหน่งก่อนหน้าและตำแหน่งหลัง (ไปป์)

ถ้านี่เป็นความจริงเราจะคืนค่า x โดยที่ B เป็นจริง
มิฉะนั้นเราจะเรียกคืนโดยไม่มีตำแหน่งที่แท้จริง


0

สกาล่า 129 ไบต์

แข็งแรงเล่นกอล์ฟ

def x(a:List[Int]):Int={val (y,n)=(0+:a:+0).sliding(3).toList.partition(l=>l.max==l(1));if(y.length>1)x(n.map(_(1)))else y(0)(1)}

Ungolfed

def whoIsTallest(a: List[Int]): Int = {
  val (handUp, handDown) = (0 +: a :+ 0).sliding(3).toList.partition {
    case x :: y :: z :: Nil => y > x && y > z
  }
  if (handUp.length > 1)
    whoIsTallest(handDown.map(_(1)))
  else
    handUp.head(1)
}

ด้วยการเติมรายการซ้ายและขวาด้วย 0 สามารถจัดกลุ่มในชุดที่ 3 และแบ่งรายการสำหรับมือที่อยู่ด้านซ้ายและขวาองค์ประกอบส่วนใหญ่เปรียบเทียบกับ 0 ด้านนอกเพื่อให้ได้ตัวเลขที่ถูกต้อง (สมมติว่าความสูงของขุนนาง เป็นลบ!)


0

C ++ 14, 182 ไบต์

#define P .push_back(c[i]);
int f(auto c){decltype(c)t,s;int i=0;(c[0]>c[1]?t:s)P for(;++i<c.size()-1;)(c[i-1]<c[i]&&c[i]>c[i+1]?t:s)P(c[i-1]<c[i]?t:s)P return t.size()<2?t[0]:f(s);}

เรียนรู้ว่าตัวดำเนินการประกอบไปด้วยสามารถใช้กับวัตถุ C ++ ต้องมีการป้อนข้อมูลที่จะเป็นภาชนะที่เข้าถึงโดยสุ่มด้วยpush_backเช่นvector, และdequelist

สร้างสองตู้คอนเทนเนอร์tและsชนิดเดียวกันและต่อท้ายส่วนที่สูงที่สุดtและส่วนที่เหลือต่อsท้าย ถ้ามีเพียง 1 องค์ประกอบในtการกลับมาที่หนึ่งโทร recursive sมิฉะนั้นตัวเองด้วย

Ungolfed:

int f(auto c){
  decltype(c)t,s;
  int i=0;
  (c[0]>c[1] ? t : s).push_back(c[i]);
  for(;++i<c.size()-1;)
    (c[i-1]<c[i]&&c[i]>c[i+1] ? t : s).push_back(c[i]);
  (c[i-1]<c[i] ? t : s).push_back(c[i]);
  return t.size()<2 ? t[0] : f(s);
}

0

R, 83 ไบต์

สองรุ่นที่แตกต่างกัน:

อันนี้ใช้เวกเตอร์ N:

while(T){Z=diff(sign(diff(c(0,N,0))))<0;if(sum(Z)>1)N=N[!Z]else{print(N[Z]);break}}

อันนี้สร้างฟังก์ชั่น F ที่กำหนดซ้ำ:

F=function(N){Z=diff(sign(diff(c(0,N,0))))<0;if(sum(Z)>1)F(N[!Z])else return(N[Z])}

โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.