เลือกรายการให้เรียบ


20

พิจารณากระบวนการ "เลือก" รายการที่ซ้อนกัน การเลือกมีการกำหนดดังนี้:

  • หากอาร์กิวเมนต์เป็นรายการให้นำองค์ประกอบจากรายการโดยการสุ่ม (สม่ำเสมอ) แล้วเลือกจากสิ่งนั้น
  • หากการโต้แย้งไม่ใช่รายการเพียงแค่ส่งคืน

ตัวอย่างการนำไปใช้ใน Python:

import random
def pick(obj):
    if isinstance(obj, list):
        return pick(random.choice(obj))
    else:
        return obj

เพื่อความง่ายเราจะสมมติว่ารายการแบบซ้อนมีเพียงจำนวนเต็มหรือรายการแบบซ้อน

หากมีรายการใด ๆ ก็เป็นไปได้ที่จะสร้างเวอร์ชันที่แบนราบซึ่งไม่สามารถแยกออกได้pickเช่นการเลือกจากรายการนั้นให้ผลลัพธ์ที่เหมือนกันโดยมีความน่าจะเป็นเหมือนกัน

ตัวอย่างเช่น "pick-flattening" รายการ

[1, 2, [3, 4, 5]]

ให้ผลผลิตรายการ

[1, 1, 1, 2, 2, 2, 3, 4, 5]

. เหตุผลที่เรียบง่ายไม่ถูกต้องเนื่องจากองค์ประกอบของรายการย่อยมีความน่าจะเป็นต่ำกว่าที่จะถูกเลือกเช่นในรายการ[1, [2, 3]]1 มีโอกาสที่จะถูกเลือก 2/4 = 1/2 ในขณะที่ 3 และ 4 ทั้งคู่มี 1/4 โอกาสแต่ละ

โปรดทราบว่าการเลือกจากรายการซิงเกิลเทียบเท่ากับการเลือกจากองค์ประกอบและการเลือกจากรายการว่างเปล่านั้นไม่มีความหมาย

ความท้าทาย

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

นี่คือดังนั้นคำตอบที่สั้นที่สุดที่ถูกต้อง (วัดเป็นไบต์) ชนะ

ข้อมูลจำเพาะ

  • อินพุต[2, 3, 4], [2, 2, 2, 2, 2, 3, 3, 3, 3, 3, 4, 4, 4, 4, 4]และ[2, [3, 3], [[4]]]มีค่าเท่ากัน (เช่นพวกเขาควรให้ผลลัพธ์ที่เทียบเท่ากัน)
  • เอาท์พุท[2, 2, 2, 2, 3, 3, 3, 3]และ[2, 3]เทียบเท่า (เช่นอาจเป็นเอาท์พุท)
  • คุณสามารถสันนิษฐานได้ว่าตัวเลขในช่วงรวม 1-100 จะปรากฏในรายการ
  • คุณสามารถสมมติว่าอินพุตระดับบนสุดจะเป็นรายการนั่น2คือไม่ใช่อินพุตที่ถูกต้อง
  • คุณสามารถใช้เป็นตัวแทนที่เหมาะสมใด ๆ ของรายการที่ซ้อนกันตัวอย่างเช่น:
    [1, [2, 3]], 1 {2 3}, "[ 1 [ 2 3 ] ]"ฯลฯ
  • แทนที่จะเป็นรายการคุณสามารถส่งออกชุดข้อมูลหลายชุดหรือการจับคู่หรือเนื่องจากอนุญาตให้ใช้เฉพาะตัวเลขในช่วง 1-100 เท่านั้นรายการความยาว 100 ที่เป็นจำนวนเต็มแทนปริมาณ

กรณีทดสอบ

โปรดทราบว่าผลลัพธ์ที่แสดงรายการเป็นเพียงความเป็นไปได้ที่ถูกต้องเท่านั้น ดูข้อกำหนดสำหรับสิ่งที่ประกอบด้วยอินพุตหรือเอาต์พุตที่ถูกต้อง

format:
input -> output
[3]                          -> [3]
[1, [1, 1]]                  -> [1]
[1, [2, 3]]                  -> [1, 1, 2, 3]
[2, 3, [4, [5, 5, 6], 6, 7]] -> [2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 4, 4, 4, 5, 5, 6, 6, 6, 6, 7, 7, 7]
[[1, 1, 2], [2, 3, 3]]       -> [1, 2, 3]
[[1, 1, 2], [2, 3, 3, 3]]    -> [1, 1, 1, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3]

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

@Uriel แน่นอน; ฉันจะตั้งชื่อมันใหม่
แยกผลไม้

คำตอบ:


8

ภาษา Wolfram (Mathematica) , 41 20 ไบต์

Flatten@*Tuples//@#&

ลองออนไลน์! ไม่สนใจคำเตือนมากมายมันใช้ได้ผลในที่สุด

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

สำหรับรายชื่อของความลึก 2 เช่น{{1,2},{3},{4,5,6}}, Tuplesจะสร้างรายการ{{1,3,4},{1,3,5},{1,3,6},{2,3,4},{2,3,5},{2,3,6}}ที่สอดคล้องกับวิธีการทั้งหมดที่จะเลือกองค์ประกอบจาก{1,2} และเลือกองค์ประกอบจาก{3} และ{4,5,6}เลือกองค์ประกอบจาก

ถ้าเราFlattenนี้แล้วเราจะได้รับองค์ประกอบทั้งหมดที่มีความถี่ที่ถูกต้องเพราะการเลือกองค์ประกอบจากหนึ่งของ{1,2}, {3}หรือ{4,5,6}เทียบเท่ากับการเลือกองค์ประกอบจากทั้งหมดของพวกเขาแล้วเลือกที่หนึ่งที่จะให้

เราใช้//@เพื่อใช้สิ่งนี้ในทุกระดับของอินพุต ในกระบวนการ Mathematica บ่นมากเพราะมันเปลี่ยนอะตอมเช่น17เข้าไปTuples[17]ซึ่งมันไม่ควรจะเป็นอะไร แต่สิ่งเหล่านี้ทำให้ผลลัพธ์ที่ถูกต้องง่ายขึ้นในภายหลัง ( Tuplesมีความสุขที่จะปฏิบัติต่อTuples[17]รายการความยาว 1 แม้ว่ามันจะมีหัวอื่นที่ไม่ใช่List) ดังนั้นการบ่นจึงไม่เกี่ยวข้อง



4

เยลลี่ , 9 8 ไบต์

߀Œp$¬¡F

ลองออนไลน์!

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

߀Œp$¬¡F  Main link. Argument: x (array or positive integer)

     ¬    Compute elementwise logical NOT of x: a non-empty array for a non-empty array, 0 for a positive integer.
      ¡   Apply the link to the left once if ¬ returned a non-empty
          array, zero timed if it returned 0.
    $     Monadic chain:
߀            Map the main link over x.
  Œp          Take the Cartesian product.
       F  Flatten the result.


1

Python 2 , 128 ไบต์

def f(l,p=0):m=reduce(int.__mul__,[i*0<[]or len(i)for i in l]);return p*(p==l)or f(sum([(([i],i)[i*0>0]*m)[:m]for i in l],[]),l)

ลองออนไลน์!

พอร์ตคำตอบของเยลลี่ของฉัน

-12 ขอบคุณที่โจนาธาน Frech


ผมคิดว่าอาจจะเป็นtype(i)==int i*0<[]
Jonathan Frech

@JonathanFrech แน่นอนว่า0<[]... และtype(i)==listสามารถi*0>0;)
Erik the Outgolfer

1

C (gcc) , 234 223 ไบต์

h[9][101];o[101];n[9];l;L;e;main(x){for(;(x=scanf("%d",&e))>=0;x?++h[l][e],++n[l]:(e=getchar())-'['?e-']'?0:--l:++l>L&&++L);for(e=1,l=L+1;l--;){for(x=101;--x;o[x]+=e*h[l][x]);e*=n[l];}while(o[x]--?printf("%d ",x):++x<101);}

ลองออนไลน์!

คำอธิบาย:

h[9][101];  // <- number occurences per nesting level
o[101];     // <- number occurences in "flattened" array
n[9];       // <- number of entries per nesting level
l;          // <- current nesting level
L;          // <- max nesting level
e;          // <- multi-purpose temporary
main(x){    // x: multi-purpose temporary
    for(;
            // while not EOF try reading number
            (x=scanf("%d",&e))>=0;

            // number was read?
            x

                // then increment occurence and # entries in level
                ?++h[l][e],++n[l]

                // else read any character ... if not [
                :(e=getchar())-'['

                    // if not ]
                    ?e-']'

                        // do nothing
                        ?0

                        // else decrement nesting level
                        :--l

                    // else increment nesting level and adjust max level
                    :++l>L&&++L);

    // init factor in e to 1, iterate over nesting level from innermost
    for(e=1,l=L+1;l--;){

        // iterate over all numbers
        for(x=101;
                --x;

                // add factor times occurence on current level to output
                o[x]+=e*h[l][x]);

        // multiply factor by number of entries on current level
        e*=n[l];
    }

    // iterate over all numbers and output count times
    while(o[x]--?printf("%d ",x):++x<101);
}



0

JavaScript (ES6), 132 131 ไบต์

f=A=>(_=(a,m)=>[].concat(...a.map(m)),n=1,A=A.map(a=>a.map?f(a):[a]),_(A,a=>n*=a.length),_(A,a=>_(a.map(x=>Array(n/a.length).fill(x)))))

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