เลิกทำอาร์เรย์


34

ความท้าทายนี้ได้แรงบันดาลใจจากคำถามเกี่ยวกับ Mathematica.SE

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

[[[1, 3], 2], [1, 4], 12, [[0, [], 0], [5, [7]]]]

บางครั้งมันจะสะดวกกว่าที่จะแผ่แบนรายการนั้นเพื่อทำการจัดการบางอย่างของโหนดเช่น

--> [1, 3, 2, 1, 4, 12, 0, 0, 5, 7]
--> [1, 1, 0, 1, 0, 0, 0, 0, 1, 1]

แต่ในที่สุดคุณต้องการรักษาโครงสร้างดั้งเดิมเอาไว้ดังนั้นคุณต้องเปลี่ยนสิ่งนี้กลับเป็น

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

งานของคุณคือทำตามขั้นตอนสุดท้ายนั้น

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

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

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

ข้อ จำกัด อีกหนึ่งข้อ: คุณต้องไม่ใช้นิพจน์ทั่วไป นี่คือความท้าทายการจัดการอาร์เรย์ไม่ใช่ความท้าทายการจัดการสตริง

นี่คือรหัสกอล์ฟดังนั้นคำตอบที่สั้นที่สุด (เป็นไบต์) ชนะ

กรณีทดสอบ

Structure                             Values                 Result
[[[1,3],2],[1,4],12,[[0,0],[5,[7]]]]  [1,1,0,1,0,0,0,0,1,1]  [[[1,1],0],[1,0],0,[[0,0],[1,[1]]]]
[[[0,0],0],[0,0],0,[[0,0],[0,[0]]]]   [1,1,0,1,0,0,0,0,1,1]  [[[1,1],0],[1,0],0,[[0,0],[1,[1]]]]
[]                                    []                     []
[[]]                                  []                     [[]]
[0,1,2,3]                             [5,1,0,5]              [5,1,0,5]
[[[[[0]]]]]                           [123]                  [[[[[123]]]]]
[0,[1,[]],[[]],[2,3],[]]              [1,6,1,8]              [1,[6,[]],[[]],[1,8],[]]

มันอนุญาตหรือไม่ถ้าค่าในอาร์เรย์โครงสร้างเปลี่ยนไป?
ProgramFOX

@ProgramFOX ใช่ "คุณสามารถแก้ไขอาร์เรย์อินพุตในรหัสของคุณได้"
Martin Ender

กระแทกแดกดันหนึ่งในผลงานที่นี่อยู่ใน Mathematica
Isiah Meadows

1
@impinball นั่นคือของฉันที่ฉันโพสต์พร้อมกับคำถามเพื่อป้องกันไม่ให้คนอื่นขโมยคำตอบจากคำถามที่เชื่อมโยง (และในความเป็นจริงมันเป็นเพียงเวอร์ชัน golfed ลงของคำตอบนั้น)
Martin Ender

@ MartinBüttnerโอ้ ดี มันเป็นคำตอบที่สั้นกว่าเช่นกัน
Isiah Meadows

คำตอบ:


9

CJam, 18 16 13 ไบต์

lA,sNerN%l~]z

รับอินพุตผ่าน STDIN ในรูปแบบเดียวกับคำตอบ CJam ก่อนหน้า:

[0 [11 []] [[]] [2 3] []]
[1 6 1 8] 

และส่งออกสตริงผลลัพธ์ไปที่ STDOUT

[1 [6 []] [[]] [1 8] []]

ฉันเพียงแค่ปฏิบัติกับบรรทัดแรกเป็นสตริงแปลงอักขระตัวเลขทั้งหมดเป็นบรรทัดใหม่แบ่งเป็นหนึ่งหรือหลายครั้งของการขึ้นบรรทัดใหม่ใส่บรรทัดที่สองเป็นอาร์เรย์บนสแต็กห่อในอาร์เรย์และซิปทั้งสองอาร์เรย์ (แถว) การพิมพ์เป็นไปโดยอัตโนมัติและเป็นแถวแรกที่ถือว่าเป็นสตริงจะยังคงวงเล็บ

การขยายรหัส

lA,sNerN%l~]z
l                     "Read the first line of input. This is the nested array";
 A,s                  "Get array [0,1,2...9] and  convert it to string '012..9'";
    Ner               "Replace all occurrences of 0,1,2,..9 with new line";
       N%             "Split on one or more occurrences of new line";
         l~           "Read the second line as an array";
           ]          "Wrap both the splitted string and the second line array";
                      "in an array";
            z         "Transpose the array, there by placing the numbers from second";
                      "input array in the split holes of first input string";

ขอบคุณ @ user23013 สำหรับการบันทึก 3 ไบต์

ลองออนไลน์ได้ที่นี่


จาก OP "นี่คือความท้าทายการจัดการอาร์เรย์ไม่ใช่ความท้าทายในการจัดการสตริง"
atk

@ atk: มันสามารถโต้เถียงได้เนื่องจาก OP ไม่อนุญาตให้แสดงออกปกติเท่านั้น
n̴̖̋h̷͉̃a̷̭̿h̸̡̅ẗ̵̨́d̷̰̀ĥ̷̳

1
สั้นสำหรับ:/La- %
jimmy23013

@ user23013 ว้าวไม่เคยใส่ใจที่จะรู้ว่า%มันมีไว้เพื่อแยกเช่นกันและมันก็แยกออกเป็นหลายเหตุการณ์เช่นกัน!
เครื่องมือเพิ่มประสิทธิภาพ

@ atk ใช่เนื่องจากมีเพียงการห้าม regex ฉันใช้เทคนิคนี้
เครื่องมือเพิ่มประสิทธิภาพ

25

JavaScript, ES6, 44 ไบต์

f=(a,b,i=0)=>a.map(x=>x.map?f(x,b,i):b[i++])

สิ่งนี้จะสร้างฟังก์ชั่นfที่สามารถเรียกได้ว่าเป็น

f([0,[1,[]],[[]],[2,3],[]],[1,6,1,8])

เช่นอาร์เรย์ที่ซ้อนกันและอาร์เรย์ค่าเป็นอาร์กิวเมนต์อินพุต เอาต์พุตของฟังก์ชันคืออาร์เรย์ที่ซ้อนกันที่ถูกแปลง

คำถามนี้เป็นคำถามที่ดีมากสำหรับการเรียกซ้ำนั่นคือเหตุผลที่คำตอบคือฟังก์ชั่นการเรียกซ้ำที่เป็นระเบียบและหวาน ฉันสร้างฟังก์ชั่นfที่แปลงอาร์กิวเมนต์แรกโดยใช้mapวิธีการ สำหรับแต่ละองค์ประกอบถ้าองค์ประกอบคืออาร์เรย์จะเรียกfอีกครั้งมิฉะนั้นสำหรับจำนวนเต็มจะได้รับฉันTHiรายการและผลตอบแทนที่คุ้มค่าที่เพิ่มขึ้นของ ค่าของiถูกส่งลงในการเรียกซ้ำแต่ละครั้งเพื่อรักษาลำดับที่ถูกต้อง

การตรวจจับ Array vs. Integer นั้นทำได้อีกครั้งโดยใช้mapวิธีการนี้ สำหรับตัวแปรอาเรย์mapเป็นฟังก์ชั่นที่ถูกต้องในขณะที่ตัวแปรจำนวนเต็มไม่มีคุณสมบัติหรือฟังก์ชั่นที่เรียกว่าmapกำหนดไว้สำหรับตัวแปร

ใช้งานได้กับเบราว์เซอร์ Firefox ล่าสุด (เนื่องจาก ES6)


3
ฉันรู้ว่าฉันควรหลีกเลี่ยงความคิดเห็นเช่น "+1" และ "ขอบคุณ" แต่ไอ้นี่คือฟังก์ชั่น ES6 อันแสนหวาน! ฉันสามารถดูรหัสสายนี้สำหรับชั่วโมง :)
จาค็อบ

ฉันเห็นว่ามี 2 .mapอยู่ในรหัส มีวิธีการย่อให้สั้นลงหรือไม่ อย่างไรก็ตามรหัสที่ดี!
Derek 朕會功夫

แล้ว ES ได้เพิ่มไวยากรณ์แลมบ์ดานั้นเมื่อใด
ปุย


@Derek 朕會功夫ไม่น่าเสียดายที่ mapเชื่อมโยงกับบริบทดังนั้นแผนที่แรกจึงเป็นของaในขณะที่แผนที่ถัดไปเป็นของแต่ละแผนที่xในการทำซ้ำ ไม่มีวิธีที่สั้นกว่าในการอ้างอิงmapอย่างใดอย่างหนึ่งและไม่มีความแตกต่างของอาร์เรย์จากจำนวนเต็ม
เครื่องมือเพิ่มประสิทธิภาพ

18

JavaScript, ES6, 41 ไบต์

ฉันประทับใจมากกับคำตอบของเครื่องมือเพิ่มประสิทธิภาพมันทำอย่างชาญฉลาดและฉันเรียนรู้มากมาย อย่างไรก็ตามในการดูมันฉันพบวิธีการทำให้สั้นลงเล็กน้อยและแก้ไขข้อบกพร่องเล็ก ๆ :

f=(a,b)=>a.map(x=>x.map?f(x,b):b.shift())

ผมเอาออกตัวแปรและแทนที่มันด้วยi shift()สิ่งนี้ทำให้สั้นลงเล็กน้อยและแก้ไขปัญหาด้วยความจริงที่iส่งผ่านค่าและไม่ใช่โดยการอ้างอิงแม่มดทำให้ตัวเลขบางตัวจากอาร์เรย์สุดท้ายทำซ้ำและบางส่วนในตอนท้ายไม่ควรใช้ อีกครั้งคำตอบของเครื่องมือเพิ่มประสิทธิภาพนั้นคิดออกมาดีกว่าที่ฉันจะทำได้ฉันแค่แก้ไขมันเล็กน้อย


2
กอล์ฟดี! เศร้าเล็กน้อยที่ฉันไม่เข้าใจว่า: P
เครื่องมือเพิ่มประสิทธิภาพ

16

Dyalog APL, 14 ตัวอักษร

(∊a)←bนี่คือไม่มีเกมง่ายๆ:

โดยทั่วไป∊aหมายถึงaแบน แต่เมื่อมันเกิดขึ้นที่ด้านซ้ายมือของการมอบหมายมันจะทำสิ่งที่ปัญหานี้ถาม เพื่อให้สอดคล้องกับข้อกำหนดของการเป็นฟังก์ชันมันจำเป็นต้องมี squiggles พิเศษบางอย่าง{a←⍺⋄(∊a)←⍵⋄a}(วงเล็บปีกกาสำหรับแลมบ์ดาและสำหรับอาร์กิวเมนต์ซ้ายและขวา; สำหรับตัวคั่นคำสั่ง)

ทดสอบที่ tryapl.org โปรดทราบว่าใน APL เวกเตอร์ตัวเลขที่ว่างจะแสดงแทนด้วย("zilde") เวกเตอร์แบบองค์ประกอบเดียวถูกสร้างด้วย(,A)เพราะ(A)จะหมายถึงสเกลาร์ ในผลลัพธ์สิ่งนี้:

┌⊖┐
│0│
└~┘

แสดงถึงเวกเตอร์ตัวเลขที่ว่างเปล่า 0ในศูนย์แสดง "องค์ประกอบแม่บท" ซึ่งไม่ได้เป็นองค์ประกอบของอาร์เรย์


1
การแสดงกราฟิกนั้นไม่แยกความแตกต่าง(,1)และ(1)หรือทำไมบิตสุดท้ายจึงแสดง[1|1]แทน[1|[1]]?
Martin Ender

การแสดงแบบกราฟิกที่ tryapl ใช้ (เรียกว่า]box on) จะไม่แยกความแตกต่างระหว่างสิ่งเหล่านั้น มีฟังก์ชั่นอื่นใน Dyalog ( displayจากdfns.dws) ที่สร้างความแตกต่าง แต่น่าเสียดายที่ tryapl จะ จำกัด การโหลดพื้นที่ทำงานเพิ่มเติม (เช่นไลบรารี) :(
ngn

1
∊{0=⍴⍴⍵:⍕⍵ ⋄ '['(∇¨⍵)']'}aหากต้องการเห็นผลในรูปแบบตารางวงเล็บลองนี้: หรือสิ่งนี้: ∊{0=⍴⍴⍵:⍕⍵ ⋄ '['(1↓,'|',[1.5]∇¨⍵)']'}aถ้าคุณยืนยันในตัวคั่น, |.
ngn

โอ้คุณสามารถใช้งานได้]display aใน tryapl มันให้ข้อมูลที่สมบูรณ์เกี่ยวกับโครงสร้าง ขออภัยฉันไม่เข้าใจสิ่งนี้ในตอนแรก
ngn

จุดยุติธรรม ฉันเปลี่ยนมันเป็นฟังก์ชั่นที่มีราคาเพิ่มขึ้น 2 ไบต์
ngn

10

Python 51

f=lambda a,b:[b.pop(0)if x<[]else f(x,b)for x in a]

ตัวอย่าง:

>>> f([0,[1,[]],[[]],[2,3],[]], [1,6,1,8])
[1, [6, []], [[]], [1, 8], []]

10

Python 2, 50

f=lambda s,v:v.pop(0)if s<[]else[f(x,v)for x in s]

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

sเป็นโครงสร้างและvเป็นรายการแบบเรียบของรายการ แนวคิดคือการตรวจสอบว่าsเป็นจำนวนเต็มด้วยหรือไม่s<[](Python 2 ถือว่าตัวเลขมีขนาดเล็กกว่ารายการ) ถ้ามันเป็นเพียงแค่ใช้เวลาและกลับองค์ประกอบแรกของการลบได้จากv vมิฉะนั้น recurse sลงบนรายการย่อยของ

นี่pop เป็นชิ้นส่วนของเวทมนตร์ที่จำเป็นในโค้ดสไตล์ที่ใช้งานได้ดีมาก เนื่องจากvจุดทั้งหมดไปยังอินสแตนซ์เดียวกันการ popping องค์ประกอบจากหนึ่งจะลบออกจากvในแผนผังการดำเนินการทั้งหมดดังนั้นแต่ละหมายเลขvจะใช้เพียงครั้งเดียว รายการความเข้าใจ[f(x,v)for x in s]สร้างทรีการเรียกที่ถูกขยายความลึกก่อนและจากซ้ายไปขวาทำให้องค์ประกอบของvslotted ในลำดับที่ถูกต้อง

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

เราสามารถบันทึก char เป็น49ถ้าเราขยายข้อกำหนดการป้อนเพื่อรับค่าจาก STDIN และโครงสร้างเป็นอาร์กิวเมนต์ของฟังก์ชัน mapนี้จะช่วยให้เราใช้

v=input()
g=lambda s:v.pop(0)if s<[]else map(g,s)

9

ทับทิม, 39

f=->a,b{a.map{|d|f[d,b]}rescue b.shift}

วนซ้ำจนกว่าองค์ประกอบในรายการจะเป็นจำนวนเต็ม
เนื่องจากการเรียก Integer.map ให้ข้อยกเว้น
มันจะไปยังส่วนช่วยเหลือซึ่ง "pops / shift" องค์ประกอบที่ 1 จากรายการที่ 2

Regex soln ... อีกต่อไป:

f=->a,b{eval a.to_s.split(/\d+/).zip(b)*''}

ลองกับกรณีทดสอบ


สำหรับการอ้างอิงเท่านั้นโซลูชัน regex ไม่ได้รับอนุญาต ;)
Martin Ender

5

CJam, 43 37 35 33 ไบต์

อันนี้เป็นการแปลงคำตอบ JSของฉันโดยตรง ค่อนข้างยาวซึ่งส่วนใหญ่ใช้การตรวจจับชนิด

q~:B;{{_`La`&{F}{;BW):W=}?}%}:F~`

ใช้สองอินพุตอาร์เรย์ในสองบรรทัดของ STDIN

[[[1 3] 2] [1 4] 12 [] [[0 0] [5 [7]]]]
[1 1 0 1 0 0 0 0 1 1]

และส่งออกไปยัง STDOUT เช่น

[[[1 1] 0] [1 0] 0 "" [[0 0] [1 [1]]]]

ลองออนไลน์ได้ที่นี่


5

Haskell, 113 104 ไบต์ (86 + 18 จากการประกาศประเภทข้อมูล)

data N=I Int|L[N]
L[]!v=(L[],v)
L(a:b)!v|(c,w)<-a!v,(L d,u)<-L b!w=(L$c:d,u)
_!(n:m)=(I n,m)
s#v=fst$s!v

Haskell ไม่มีประเภทข้อมูลอาร์เรย์ที่ซ้อนกันในตัวดังนั้นฉันจึงต้องม้วนตัวเอง ด้วยเหตุผลนี้โปรแกรมจึงมีเพียงการจับคู่รูปแบบและการเรียกซ้ำโครงสร้างอย่างชัดเจน กรณีทดสอบสุดท้ายอ่าน

L[I 0,L[I 1,L[]],L[L[]],L[I 2,I 3],L[]]#[1,6,1,8]

และประเมินผลให้

L[I 1,L[I 6,L[]],L[L[]],L[I 1,I 8],L[]]

4

Mathematica, 41 ไบต์

Function[,m[[i++]],Listable][i=1;m=#2;#]&

นี่คือฟังก์ชันที่ไม่มีชื่อซึ่งใช้โครงสร้างเป็นอาร์กิวเมนต์แรกและรายการค่าเป็นอาร์กิวเมนต์ที่สอง (และส่งกลับรายการ)

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

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

  • เรากำหนดListableฟังก์ชั่นที่บริสุทธิ์ ฟังก์ชั่น Listable ถูกนำมาใช้โดยอัตโนมัติเพื่อให้องค์ประกอบของการโต้แย้งรายการ (ซ้ำ) แทนของรายการตัวเองเพื่อเรียกร้องfในรายการโครงสร้างโดยทั่วไปจะกลับรายการของโครงสร้างเดียวกันกับแต่ละจำนวนเต็มแทนที่ด้วยif[i]
  • เราเก็บรายการค่าในระดับโลกและในเคาน์เตอร์mi
  • แต่ละคนที่เราเรียกเวลาf(โดยไม่คำนึงถึงการโต้แย้ง) mเรากลับองค์ประกอบต่อไปของ

4

รีโบล - 87 66 60

f: func[a[block!]b][map-each n a[any[attempt[f n b]take b]]]

Ungolfed:

f: func [a [block!] b] [
    map-each n a [
        any [
            attempt [f n b]  
            take b
        ]
    ]
]

ตัวอย่าง:

>> f [0 [1 []] [[]] [2 3] []]   [1 6 1 8]           
== [1 [6 []] [[]] [1 8] []]

4

C #, 225 + 13 = 239 185 + 35 = 220 172 + 35 = 207 ไบต์

ต้องการสิ่งนี้:

using System;using o=System.Object;

ยอมรับobject[]s เป็นอาร์กิวเมนต์

o[]u(o[]a,o[]b){var c=a;int i=0;Action<o[],o[]>d=null;d=(e, f)=>{for(int j=0;j<e.Length;j++){if(e[j]is int){f[j]=b[i];i++;}else{d((o[])e[j],(o[])f[j]);}}};d(a,c);return c;}

รหัสไม่ได้รับการตอบกลับ:

object[] Unflatten(object[] structure, object[] values)
{
    var c = structure;
    int i = 0;
    Action<object[], object[]> recursiveFunc = null;
    recursiveFunc = (e, f) =>
    {
        for (int j = 0; j < e.Length; j++)
        {
            if (e[j] is int)
            {
                f[j] = values[i]; i++;
            }
            else
            {
                recursiveFunc((object[])e[j], (object[])f[j]);
            }
        }
    };
    recursiveFunc(structure, c);
    return c;
}

2
คุณสามารถย่อให้สั้นลงอีกเล็กน้อยโดยใช้using o=System.Objectและเปลี่ยนทุกกรณีที่มีเพียงแค่object msdn.microsoft.com/en-us/library/sf0df423.aspxo
Kroltan

1
@Kroltan เคล็ดลับเยี่ยมมากขอบคุณ!
ProgramFOX

Cloneตื้น หากอนุญาตให้ดัดแปลงอินพุตคุณไม่จำเป็นต้องโคลนเลย หากไม่ได้รับอนุญาตคุณต้องทำการโคลนนิ่งอย่างเหมาะสม
CodesInChaos

@CodesInChaos ฉันเห็น เมื่อปรับเปลี่ยนอาร์เรย์อินพุตได้รับอนุญาตฉันลบโคลน ขอบคุณ!
ProgramFOX

3

Python 2, 64 ไบต์

def g(N,L):f=lambda N:L.pop(0)if`N`<":"else map(f,N);return f(N)

ฉันได้ยินว่าคุณชอบรายการในรายการดังนั้นฉันจึงใส่ฟังก์ชั่นในฟังก์ชั่น

แก้ไข: ดูคำตอบของ grcตอนนี้ฉันรู้ว่าไม่จำเป็นอย่างสมบูรณ์ โอ้ดี ...


3

SWI-Prolog 82

f([],A,[],A):-!.
f([H|T],A,[J|U],B):-(is_list(H),!,f(H,A,J,C);A=[J|C]),f(T,C,U,B).

วิ่งตัวอย่าง:

?- f([[[1,3],2],[1,4],12,[[0,[],0],[5,[7]]]],[1,1,0,1,0,0,0,0,1,1],R,[]).
R = [[[1,1],0],[1,0],0,[[0,[],0],[1,[1]]]].

[]คำถามสุดท้ายในการตรวจสอบจำนวนองค์ประกอบที่ไม่ตรงกันซึ่งดูเหมือนจะไม่จำเป็นสำหรับคำถามนี้


อะไรทำให้การตัด (และโดยส่วนขยายมีราคาแพงis_list) จำเป็น?
สตริงที่ไม่เกี่ยวข้อง

1
@ UnrelatedString: อย่าลังเลที่จะแก้ไขคำตอบโดยตรงหากคุณไม่จำเป็นต้องได้รับคำตอบที่ถูกต้อง อารัมภบทของฉันไม่ดีในตอนนั้น (ฉันใช้ห้องสมุดและการตัดอย่างกว้างขวาง) และยิ่งเป็นสนิมในวันนี้
n̴̖̋h̷͉̃a̷̭̿h̸̡̅ẗ̵̨́d̷̰̀ĥ̷̳

2

Erlang, 116 93 Bytes

f(R,F)->put(n,F),[g(X)||X<-R].
g([H|T])->[g(H)|g(T)];g([])->[];g(E)->[H|T]=get(n),put(n,T),H.

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


1

Perl 5, 49 ไบต์

อาร์กิวเมนต์แรกคือโครงสร้างแม่แบบที่สองคือค่า

sub u{($t,$l)=@_;ref$t?[map{u$_,$l}@$t]:shift@$l}

โปรแกรมทดสอบ

use Test::More;
use Test::Deep;

sub u{($t,$l)=@_;ref$t?[map{u$_,$l}@$t]:shift@$l}

cmp_deeply u([[[1,3],2],[1,4],12,[[0,0],[5,[7]]]],[1,1,0,1,0,0,0,0,1,1]),[[[1,1],0],[1,0],0,[[0,0],[1,[1]]]];
cmp_deeply u([[[0,0],0],[0,0],0,[[0,0],[0,[0]]]],[1,1,0,1,0,0,0,0,1,1]),[[[1,1],0],[1,0],0,[[0,0],[1,[1]]]];
cmp_deeply u([], []), [];
cmp_deeply u([[]], []), [[]];
cmp_deeply u([0,1,2,3], [5,1,0,5]), [5,1,0,5];
cmp_deeply u([[[[[0]]]]], [123]), [[[[[123]]]]];
cmp_deeply u([0,[1,[]],[[]],[2,3],[]], [1,6,1,8]), [1,[6,[]],[[]],[1,8],[]];
done_testing;

1

PowerShell: 115

อาร์เรย์อินพุตคือ $ i การแม็พคือ $ m เอาต์พุตคือ $ o

$h={if($_.GetType().IsArray){if($_.c -eq 0){,@()}else{,@($_|%{.$h})}}else{$m[$c++]}};$i|%{$o=@();$c=0}{$o+=,(.$h)}

$ h เป็นสตริงที่มีฟังก์ชั่นวนซ้ำและคุณสามารถรันโค้ดที่มีอยู่ในสตริงด้วย $ h ... และมันจะสั้นกว่า 30 ไบต์ถ้า PowerShell ไม่ได้ยืนยันในการปรับค่าอาร์เรย์เดี่ยวให้กับสเกลาร์และอาร์เรย์ ด้วยค่า Null เดียวถึง Null

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

$j={if($_.GetType().IsArray){write-host '(' -n;($_|%{.$j});write-host ')' -n}else{write-host "$_" -n}};write-host '(' -n;$o|%{(.$j)}; write-host ')' -n;

แก้ไข: 149

บันทึกเป็น unflatten.ps1:

$m=[array]$args[1];$h={if($_.GetType().IsArray){if($_.c -eq 0){,@()}else{,@($_|%{.$h})}}else{$m[$c++]}};$args[0]|%{$o=@();$c=0}{$o+=,(.$h)};echo $o;

แก้ไข: 136, การสร้างอาร์เรย์เอาต์พุตแบบอินไลน์และการเขียนข้อมูลออก

$m=[array]$args[1];$h={if($_.GetType().IsArray){if($_.c -eq 0){,@()}else{,@($_|%{.$h})}}else{$m[$c++]}};echo(,@($args[0]|%{$c=0}{.$h}))

โทรด้วย. \ unflatten.ps1 [อาร์เรย์อินพุต] [อาร์เรย์การจับคู่]

เอาต์พุตถูกเขียนไปที่ไพพ์ไลน์ดังนั้นให้เรียกใช้สิ่งนี้ก่อน:

Function View-Array{
Param([Parameter(ValueFromPipeline=$True,ValueFromPipelinebyPropertyName=$True)]
      [array]$o)

    PROCESS{
    $j={if($_.GetType().IsArray){write-host '(' -n;($_|%{.$j});write-host ')' -n}else{write-host "$_" -n}};
    write-host '(' -n;$o|%{(.$j)}; write-host ')' -n;
    }
}

และเรียกใช้ด้วย

.\unflatten.ps1 [input array] [mapping array] | View-Array

1

C #, (40 + 123) = 163 ไบต์หรือ (67 + 81) = 148 ไบต์

C # ทนทุกข์ทรมานจากการพิมพ์แบบคงที่และเนมสเปซยาวที่นี่

วิธีการอาร์เรย์

ใช้คำสั่ง:

using o=System.Object;using System.Linq;

รหัส:

o[] u(o[] x,o[] y){int i=0;Func<o[],o[],o[]> f=null;f=(a,b)=>a.Select(e=>e is int?b[i++]:f((o[])e,b)).ToArray();return f(x,y);}

วิธีการสแต็ค (ใช้โครงสร้างสแต็กแทนอาร์เรย์)

ใช้คำสั่ง:

using s=System.Collections.Generic.Stack<object>;using System.Linq;

รหัส:

System.Func<s,s,s>f=null;f=(a,b)=>new s(a.Select(e=>e is int?b.Pop():f((s)e,b)));

ความพยายามครั้งแรกรหัสกอล์ฟครั้งแรกที่นี่

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