จำนวนของเซ็ตย่อยที่แต่ละหมายเลขตั้งแต่ 1 ถึง


11

ปัญหาของฉัน ได้รับผมต้องการที่จะนับจำนวนของมัลติถูกต้องSMultisetนั้นถูกต้องถ้าn S SnSS

  • ผลรวมขององค์ประกอบของคือและS nSn
  • ตัวเลขจากทุกเพื่อสามารถแสดงไม่ซ้ำกันเป็นผลรวมของบางส่วนขององค์ประกอบของที่S1 n1nS

ตัวอย่าง. ตัวอย่างเช่นถ้าn = 5n = 5แล้ว{ 1 , 1 , 1 , 1 , 1 } , { 1 , 2 , 2 } , { 1 , 1 , 3 }{ 1 , 1 , 1 , 1 , 1 } , { 1 , 2 , 2 } , { 1 , 1 , 3 }ที่ถูกต้อง

อย่างไรก็ตามS = { 1 , 1 , 1 , 2 }S={1,1,1,2}ไม่ถูกต้องเพราะ 2 สามารถสร้างได้ทั้ง{ 1 , 1 }{1,1}และ{ 2 }{ 2 } (เช่น 2 สามารถแสดงได้ทั้ง2 = 1 + 12 = 1 + 1และ2 = 22 = 2 ) ดังนั้นเงื่อนไขที่สองไม่ถือ ในทำนองเดียวกัน 3 สามารถเกิดขึ้นโดย{ 2 , 1 }{ 2 , 1 }และ{ 1 , 1 , 1{ 1 , 1 , 1 } }

S = { 1 , 2 , 4S= { 1 , 2 , 4 } ยังไม่ถูกต้องเพราะจำนวนทั้งหมดจาก 11ที่จะ 55สามารถทำซ้ำกัน แต่ผลรวมขององค์ประกอบของ SSไม่ได้เป็น55


ฉันพยายามหาอัลกอริทึมที่ดีสำหรับปัญหานี้มาระยะหนึ่งแล้ว แต่ไม่สามารถแก้ไขได้ มันมาจากcodechef ฉันเห็นวิธีแก้ไขปัญหาที่ส่งมาแล้วบางส่วน แต่ฉันก็ยังหาเหตุผลไม่ได้ในการแก้ปัญหา หมายเหตุ:การ จำกัด เวลาสำหรับคำถามคือ 10 วินาทีและn < 10 9n < 109

สำหรับ MultiSet ผมจะใช้สัญกรณ์S = { ( 1 , 1 ) , ( 2 , 2 ) . . } ฉัน < Jถ้าฉัน< Jซึ่งหมายความฉันเกิดขึ้นฉันครั้งใน MultiSet เอสS={(a1,c1),(a2,c2)...} ai<aji<jaici

จนถึงตอนนี้ฉันได้ข้อสรุป

  • องค์ประกอบแรกของชุดมัลติเซตที่เรียงควรเป็น11
  • ให้S = { 1 , 2k } | 12kเป็นชุดต่อไปนี้สองคุณสมบัติแล้วR < k R + 1 = R  หรือ  ( Σ R ฉัน= 0ฉัน ) + 1S={1,a2ak}|a1a2ak  r<k  ar+1=ar or (ri=0ai)+1
  • ให้S = { ( 1 , c 1 ) , ( a 2 , c 2 ) ( a k , c k ) } | 12kที่ฉันเกิดขึ้นผมครั้งต่อไปนี้คุณสมบัติที่ต้องการแล้วจากข้อสรุปดังกล่าวข้างต้นที่เราสามารถพูดได้ว่าฉันฉัน| n + 1และS={(1,c1),(a2,c2)(ak,ck)}|a1a2akaici i ai|n+1a i | Jถ้า J >ฉัน พิสูจน์: a i + 1 = ( a i c i + a i - 1 ) + 1 a i | ฉัน+ 1ai|ajj>i
    ai+1=(aici+ai1)+1ai|ai+1
  • ตอนนี้พิจารณาS = { 1 , 1 1 d - 1 , d , d d , d ม. 1 , d ม. 1ม. 1 , d ม. 2 , d ม. 2ม. 2 , }คือทั้งหมด ตัวเลขที่ตามมาหลังวันที่ 1 จะเป็นหลายd ดังนั้นขอf ( n )S={1,11d1,d,dd,dm1,dm1dm1,dm2,dm2dm2,}df(n)เป็นจำนวนของ Multiset ที่เป็นไปได้แล้วf ( n ) = d | n + 1 , d 1 f ( n - ( d - 1 )d )ที่ฉันรวมจำนวนทั้งหมดที่เป็นไปได้ของ1s(=d-1) ในแง่อื่น ๆf(n-1)=g(n)=d| n,dng(d)f(n)=d|n+1,d1f(n(d1)d)1s=d1f(n1)=g(n)=d|n,dng(d)

ในที่สุดปัญหาของฉันลดลงถึงสิ่งนี้ - หาg ( n )อย่างมีประสิทธิภาพเพื่อที่จะได้ไม่เกินเวลาที่กำหนดg(n)


2
คุณได้ทำการตรวจสอบแล้วว่าเหมาะสมหรือไม่ที่จะขอให้ผู้อื่นโพสต์คำตอบและอัลกอริทึมสำหรับปัญหาการปฏิบัติต่อสาธารณะ ดูเหมือนว่าคำถามที่พบบ่อยของ Codechef คาดหวังว่าโซลูชันจะไม่ถูกโพสต์แบบสาธารณะ (ยกเว้นปัญหาพื้นฐานบางอย่าง) การโพสต์วิธีแก้ปัญหาที่นี่จะ "ทำให้เสีย" ปัญหาการปฏิบัติสำหรับผู้อื่นหรือว่าถือว่าตกลง? ฉันไม่คุ้นเคยกับบรรทัดฐานและมารยาทของชุมชน Codechef
DW

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

1
@DW ฉันไม่คิดว่าพวกเขาจะรังเกียจถ้าเราพูดถึงเครื่องหมายที่ไม่ได้มาจากการแข่งขันอย่างต่อเนื่อง
Ravi Upadhyay

1
คุณกำลังมองหาจำนวนพาร์ติชันของหมายเลขอินพุต ฉันขอแนะนำให้คุณทำวิจัยโดยใช้ buzzword นี้
ราฟาเอล

2
@ ราฟาเอลฉันเห็นด้วยโปสเตอร์ควรอ่านเทคนิคเหล่านั้น ไม่ใช่ปัญหาเดียวกัน - เงื่อนไขแรกของผู้ลงโฆษณาต้องการให้เป็นพาร์ติชัน แต่เงื่อนไขที่สองกำหนดข้อ จำกัด เพิ่มเติม (สำหรับการเปลี่ยนแปลงที่ไม่ซ้ำกัน) - แต่อาจเป็นไปได้ที่จะใช้เทคนิคเดียวกันกับการนับจำนวน พาร์ติชันที่มีการแก้ไขบางอย่างเพื่อจัดการกับข้อกำหนดเพิ่มเติม
DW

คำตอบ:


2

นี่คือสิ่งที่ทางออกที่เร็วที่สุดกำลังทำอยู่ เป็นการคำนวณฟังก์ชันของคุณอย่างแน่นอน g ( n ) = d n d < n g ( d ) ,g ( 1 ) = 1 เมื่อได้รับ nเราคำนึงถึงมัน (ดูด้านล่าง) และคำนวณปัจจัยทั้งหมด (ดูด้านล่าง) f 1 , , f mตามลำดับบางอย่างเช่น f i | f jหมายถึง i j (คุณสมบัติ P) ตอนนี้เราคำนวณ gตามสูตรโดยดูจากปัจจัยต่างๆตามลำดับที่กำหนด คุณสมบัติ P ทำให้มั่นใจได้ว่าเมื่อเราคำนวณ g ( d )เราได้คำนวณ g ( e )สำหรับปัจจัยที่ไม่สำคัญทั้งหมดแล้ว e

ก.( n ) = dnd< nก.( d) ,ก.( 1 ) = 1
n1, , fม.ผม| Jฉันjก.ก.( d)ก.( e )อีของd นอกจากนี้ยังมีการเพิ่มประสิทธิภาพ (ดูด้านล่าง)d

ในรายละเอียดมากขึ้นเราไปกว่าปัจจัยในการสั่งซื้อและสำหรับแต่ละปัจจัยฉันเราจะพบทุกปัจจัยที่ไม่น่ารำคาญโดยการตรวจสอบซึ่ง1 , ... , ฉัน- 1แบ่งฉันผม1, , fฉัน- 1ผม

การดำเนินการ:การประมวลผลล่วงหน้า: เราทำรายการช่วงเวลาทั้งหมดที่ต่ำกว่า10 9โดยใช้ตะแกรง Eratosthenes ให้nเราแค่ใช้ส่วนทดลอง109n

การสร้างปัจจัยทั้งหมด:สิ่งนี้เกิดขึ้นซ้ำแล้วซ้ำอีก สมมติว่าn = P k 1 1พีเคทีที เราทำงานเสื้อซ้อนกันลูปลิตร1{ 0 , ... , k 1 } , ... , L เสื้อ{ 0 , ... , k T }และเอาท์พุทพีลิตร1 1พีลิตรทีที คุณสามารถพิสูจน์คุณสมบัติ P โดยการเหนี่ยวนำn = pk11หน้าkเสื้อเสื้อเสื้อล.1{ 0 , , k1} , , lเสื้อ{ 0 , , kเสื้อ}พีล.11หน้าล.เสื้อเสื้อ

การเพิ่มประสิทธิภาพ:เนื่องจากโปรแกรมทำงานบนอินพุตหลายตัวเราจึงสามารถใช้บันทึกช่วยจำเพื่อประหยัดเวลาในอินพุตที่แตกต่างกัน เราบันทึกค่าเล็ก ๆ เท่านั้น (สูงสุด10 5 ) และสิ่งนี้ช่วยให้เราสามารถเก็บค่าที่ถูกบันทึกไว้ทั้งหมดในอาร์เรย์ อาร์เรย์ได้รับการเริ่มต้นด้วยศูนย์และเราสามารถบอกได้ว่าค่าใดเป็นที่รู้จักอยู่แล้ว (เนื่องจากค่าที่คำนวณทั้งหมดเป็นค่าบวก)105


ถ้าการแยกตัวประกอบเฉพาะของn + 1คือp k 1 1 , , p k t t , ดังนั้นf ( n ) จะขึ้นอยู่กับ( k 1 , , k t )เท่านั้นและในความเป็นจริงกับรุ่นที่เรียงลำดับของเวกเตอร์นี้ . ทุกหมายเลขที่ต่ำกว่า10 9มีปัจจัยสำคัญสูงสุด29 รายการ (ด้วยการซ้ำซ้อน) และเนื่องจากp ( 29 ) = 4565ดูเหมือนว่าเป็นไปได้ที่จะคำนวณfn + 1พีk11, , pkเสื้อเสื้อ( n )( k1, , kเสื้อ)10929p ( 29 ) = 4565(หรือมากกว่าg ) สำหรับพวกเขาทั้งหมดซ้ำ ๆ วิธีนี้อาจเร็วกว่านี้ถ้ามีอินพุตที่แตกต่างกันมากมาย มันเป็นมีที่มากที่สุด10ก.10

เป็นไปได้ว่าฟังก์ชันนี้การแม็พพาร์ติชันกับg ที่สอดคล้องกันมีรูปแบบการวิเคราะห์ที่ชัดเจน ยกตัวอย่างเช่นกรัม( P k ) = 2 k - 1 , กรัม( หน้า1 ... พีที )จะได้รับโดยA000670และกรัม( P 2 1 P 2 ... พีที )จะได้รับโดยA005649หรือA172109ก.ก.( หน้าk) = 2k1g(p1pt)g(p21p2pt)


1

ตกลงดังนั้นคุณมีความสัมพันธ์ที่เกิดซ้ำสำหรับg ( ) (ดูตอนท้ายของคำถามของคุณ)g()

ณ จุดนี้ดูเหมือนว่าวิธีธรรมชาติจะเขียนอัลกอริทึมแบบเรียกซ้ำเพื่อคำนวณg ( n )และใช้การบันทึกเพื่อให้คุณไม่ต้องคำนวณg ( i )มากกว่าหนึ่งครั้ง ในคำอื่น ๆ เมื่อคุณคำนวณกรัม( ฉัน) , คุณเก็บไว้ในตารางแฮชที่แมฉันกรัม( ฉัน) ; หากคุณต้องการทราบg ( i )อีกครั้งในอนาคตคุณสามารถค้นหาได้ในตารางแฮชg(n)g(i)g(i)ig(i)g(i)

นี้ไม่จำเป็นต้องแฟnแต่มีขั้นตอนวิธีการที่มีประสิทธิภาพสำหรับแฟnเมื่อn 10 9nnn109

นอกจากนี้คุณยังอาจมีลักษณะเป็นลำดับกรัม( 1 ) , กรัม( 2 ) , กรัม( 3 ) , กรัม( 4 ) , กรัม( 5 ) , ...ใน On-Line สารานุกรมของจำนวนเต็มลำดับ หากคุณพบลำดับในสารานุกรมบางครั้งพวกเขาจะให้ข้อมูลที่เป็นประโยชน์เพิ่มเติม (เช่นอัลกอริทึมที่มีประสิทธิภาพสำหรับการคำนวณลำดับ) ที่ยอมรับว่าอาจนำความสนุกสนานจากสิ่งต่าง ๆ แม้ว่าก.( 1 ) , g( 2 ) , g( 3 ) , g( 4 ) , g( 5 ) , ...


0

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

ในรายละเอียดอีกเล็กน้อย: สมมติว่าคุณมี MultiSet S ได้รับหมายเลขฉันกับ1 ฉันnวิธีการที่คุณสามารถระบุ submultiset ของSที่จำนวนเงินที่จะฉัน ? คุณจะตรวจสอบได้อย่างไรว่าชุดข้อมูลย่อยนั้นไม่ซ้ำกัน พยายามที่จะปรับตัวเข้ากับเทคนิคการเขียนโปรแกรมแบบไดนามิกมาตรฐานสำหรับการเปลี่ยนแปลง (ดูคำถามนี้ด้วย)Sผม1 ฉันnSผม

รับ multiset Sคุณจะตรวจสอบได้อย่างไรว่ามันเป็นไปตามเงื่อนไขที่สองหรือไม่เช่นว่าทุกหมายเลขจาก 1 ถึงnสามารถแสดงได้โดยไม่ซ้ำกันเป็นผลรวมของซับเซ็ตย่อยของS (เงื่อนไขการเปลี่ยนแปลงที่ไม่ซ้ำกัน) นี่น่าจะง่ายถ้าคุณแก้ไขก่อนหน้านี้SnS

ให้P ( n )แสดงรายการของชุดมัลติที่ตรงตามเงื่อนไขของคุณ หากคุณรู้จักP ( 1 ) , P ( 2 ) , , P ( n )คุณจะใช้ข้อมูลนั้นเพื่อสร้างP ( n + 1 ) ได้อย่างไร? ที่นี่คุณอาจต้องการปรับใช้เทคนิคการเขียนโปรแกรมแบบไดนามิกมาตรฐานสำหรับการระบุพาร์ติชันของจำนวนเต็มP( n )P( 1 ) , P( 2 ) , , P( n )P( n + 1 )


นี่คือวิธีการที่อาจจะดีกว่า

สมมติว่าSเป็นมัลติเซ็ตที่ตอบสนองเงื่อนไขทั้งสองของคุณ (สำหรับn ) เราจะขยายมันเพื่อรับมัลติเซ็ตTที่มีองค์ประกอบหนึ่งมากกว่าได้อย่างไร ในคำอื่น ๆ วิธีการที่เราสามารถระบุวิธีการทั้งหมดเพื่อเพิ่มองค์ประกอบหนึ่งที่มากขึ้นในการSเพื่อให้ได้ MultiSet ใหม่Tที่ทั้งสองฝ่ายของเงื่อนไขของคุณ (บางn ' )?SnTSTn'

คำตอบ: ถ้าxสามารถแสดงเป็นผลรวมขององค์ประกอบบางอย่างของSดังนั้นจะไม่มีจุดเพิ่มลงในS : ซึ่งจะทำให้Tละเมิดเงื่อนไขที่ไม่ซ้ำกัน ดังนั้นเราสามารถแจกแจงจำนวนเต็มxทั้งหมดที่ไม่สามารถแสดงเป็นผลรวมขององค์ประกอบบางส่วนของS ; แต่ละอันเป็นสิ่งที่สามารถเพิ่มลงในSเพื่อรับมัลติเซตTใหม่ที่จะตอบสนองเงื่อนไขทั้งสอง (สำหรับnอื่น ๆ)xSSTxSSTn

ยิ่งไปกว่านั้นมันเป็นไปได้ที่จะระบุจำนวนเต็มที่สามารถแสดงเป็นผลรวมขององค์ประกอบบางอย่างของSและไม่สามารถใช้การเขียนโปรแกรมแบบไดนามิก คุณสร้างอาร์เรย์Aสองมิติ[ 1 | S | , 1 ... n ]ของ booleans ที่[ ฉัน, J ]เป็นจริงถ้ามีวิธีที่จะแสดงความจำนวนเต็มเจเป็นผลรวมของบางส่วนของแรกฉันองค์ประกอบของS (เฉพาะครั้งแรกที่ฉันองค์ประกอบของSมีสิทธิ์ที่จะ ถูกนำมาใช้; ที่SSA[1|S|,1n]A[i,j]jiSiSSเรียงลำดับแล้วดังนั้นS = { s 1 , s 2 , , s k }และs 1s 2s k ) โปรดทราบว่าA [ i , j ]สามารถคำนวณได้โดยใช้ค่าของA [ 1 i - 1 , 1 j - 1 ] : โดยเฉพาะA [ i , j ]S={s1,s2,,sk}s1s2skA[i,j]A[1i1,1j1]= [ ฉัน- 1 , J ] [ ฉัน- 1 , J - s ฉัน ]ถ้า J > s ฉันหรือ [ ฉัน, J ] = [ ฉัน- 1 , J ]มิฉะนั้น ซึ่งจะช่วยให้เราสามารถระบุตัวเลขทั้งหมดที่มีผู้สมัครที่จะเพิ่มSA[i,j]=A[i1,j]A[i1,jsi]j>siA[i,j]=A[i1,j]S

ถัดไปสำหรับแต่ละส่วนขยายของผู้สมัครTของS (ได้รับจากการเพิ่มองค์ประกอบหนึ่งไปยังS ) เราต้องการตรวจสอบว่าT เป็นไปตามเงื่อนไขทั้งสองหรือไม่ ให้nแสดงผลรวมขององค์ประกอบของSและn 'ผลรวมขององค์ประกอบของT เราจำเป็นต้องตรวจสอบว่าทุกจำนวนเต็มในช่วงn + 1 , n + 2 , , n สามารถแสดงเป็นผลรวมขององค์ประกอบบางส่วนของTT. สิ่งนี้สามารถแก้ไขได้โดยใช้การเขียนโปรแกรมแบบไดนามิกโดยใช้อัลกอริธึมมาตรฐานสำหรับการเปลี่ยนแปลง (ในความเป็นจริงถ้าคุณยังมีอาร์เรย์ดังกล่าวข้างต้นคุณสามารถขยายได้นิด ๆ หน่อย ๆ เพื่อแก้ปัญหานี้: เราทำให้มันอาร์เรย์[ 1 ... | T | , 1 ... n ' ]ให้ดำเนินการต่อเพื่อเติมเต็มในทุก ของรายการเพิ่มเติมและตรวจสอบให้แน่ใจว่าA [ | T | , n + 1 ] , A [ | T | , n + 2 ] ,, A [ | T | , n ]เป็นจริงทั้งหมด) ดังนั้นตอนนี้เราสามารถแจกแจงมัลติเซต Tทั้งหมดที่ขยาย Sด้วยองค์ประกอบเดียวและเป็นไปตามเงื่อนไขทั้งสอง

นี้แสดงให้เห็นทันทีขั้นตอนวิธีการแจกแจงทุกมัลติSที่ตอบสนองเงื่อนไขของคุณสำหรับทุกnถึงบางผูกพันพูดn 20 เราจะมีอาร์เรย์P [ 1 ... 20 ]ที่P [ 5 ]ร้านค้าทั้งหมดมัลติSรวมที่ 5 และโดยทั่วไป, P [ n ]ร้านค้าชุดของมัลติทั้งหมดSรวมที่n

ต่อไปเราสามารถเติมP [ n ]ซ้ำได้ เริ่มต้นด้วยการตั้งค่าP [ 1 ]จะมีเพียงหนึ่ง MultiSet { 1 } ถัดไปสำหรับแต่ละn (นับจาก 1 ถึง 20) สำหรับแต่ละS P [ n ]แจกแจงส่วนขยายที่เป็นไปได้ทั้งหมดTของS (โดยใช้เทคนิคด้านบน) ให้n แสดงถึงผลรวมขององค์ประกอบของTและ แทรกTเป็นP [ n ]ถ้ามันไม่ได้แล้วในปัจจุบันและถ้าn ' 20

นี่น่าจะทำได้ โชคดี! มีความสุข! การทำงานผ่านรายละเอียดจะเป็นการฝึกการเรียนรู้ที่ดีในการเขียนโปรแกรมแบบไดนามิก


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