ความท้าทายคือการเขียนรหัสที่เร็วที่สุดที่เป็นไปได้สำหรับการคำนวณHafnian ของเมทริกซ์
Hafnian ของเมทริกซ์สมมาตร - 2n
โดย - 2n
เมทริกซ์A
หมายถึง:
นี่ S 2nหมายถึงชุดของพีชคณิตทั้งหมดของจำนวนเต็มจาก1
การที่เป็น2n
[1, 2n]
ลิงก์วิกิพีเดียยังมีสูตรการค้นหาที่แตกต่างกันซึ่งอาจเป็นที่สนใจ หน้า wiki เดียวกันพูดถึงการฝึกหัด adjacency แต่รหัสของคุณควรใช้กับเมทริกซ์อื่นเช่นกัน คุณสามารถสันนิษฐานได้ว่าค่าทั้งหมดจะเป็นจำนวนเต็ม แต่ไม่ใช่ว่าเป็นค่าบวกทั้งหมด
นอกจากนี้ยังมีอัลกอริทึมที่เร็วขึ้น แต่ดูเหมือนจะเข้าใจยาก และ Christian Sievers เป็นคนแรกที่นำไปใช้ (ใน Haskell)
ในเมทริกซ์คำถามนี้ทุกสแควร์และสมมาตรมีขนาดเท่ากัน
การใช้งานอ้างอิง (โปรดทราบว่านี่ใช้วิธีที่ช้าที่สุด)
นี่คือตัวอย่างโค้ดไพ ธ อนจาก Mr. Xcoder
from itertools import permutations
from math import factorial
def hafnian(matrix):
my_sum = 0
n = len(matrix) // 2
for sigma in permutations(range(n*2)):
prod = 1
for j in range(n):
prod *= matrix[sigma[2*j]][sigma[2*j+1]]
my_sum += prod
return my_sum / (factorial(n) * 2 ** n)
print(hafnian([[-1, 1, 1, -1, 0, 0, 1, -1], [1, 0, 1, 0, -1, 0, -1, -1], [1, 1, -1, 1, -1, -1, 0, -1], [-1, 0, 1, -1, -1, 1, -1, 0], [0, -1, -1, -1, -1, 0, 0, -1], [0, 0, -1, 1, 0, 0, 1, 1], [1, -1, 0, -1, 0, 1, 1, 0], [-1, -1, -1, 0, -1, 1, 0, 1]]))
4
M = [[1, 1, 0, 0, 0, 0, 0, 1, 0, 0], [1, 1, -1, 0, -1, 1, 1, 1, 0, -1], [0, -1, -1, -1, 0, -1, -1, 0, -1, 1], [0, 0, -1, 1, -1, 1, -1, 0, 1, -1], [0, -1, 0, -1, -1, -1, -1, 1, -1, 1], [0, 1, -1, 1, -1, 1, -1, -1, 1, -1], [0, 1, -1, -1, -1, -1, 1, 0, 0, 0], [1, 1, 0, 0, 1, -1, 0, 1, 1, -1], [0, 0, -1, 1, -1, 1, 0, 1, 1, 1], [0, -1, 1, -1, 1, -1, 0, -1, 1, 1]]
print(hafnian(M))
-13
M = [[-1, 0, -1, -1, 0, -1, 0, 1, -1, 0, 0, 0], [0, 0, 0, 0, 0, -1, 0, 1, -1, -1, -1, -1], [-1, 0, 0, 1, 0, 0, 0, 1, -1, 1, -1, 0], [-1, 0, 1, -1, 1, -1, -1, -1, 0, -1, -1, -1], [0, 0, 0, 1, 0, 0, 0, 0, 0, 1, -1, 0], [-1, -1, 0, -1, 0, 0, 1, 1, 1, 1, 1, 0], [0, 0, 0, -1, 0, 1, 1, -1, -1, 0, 1, 0], [1, 1, 1, -1, 0, 1, -1, 1, -1, -1, -1, -1], [-1, -1, -1, 0, 0, 1, -1, -1, -1, 1, -1, 0], [0, -1, 1, -1, 1, 1, 0, -1, 1, -1, 1, 1], [0, -1, -1, -1, -1, 1, 1, -1, -1, 1, 0, -1], [0, -1, 0, -1, 0, 0, 0, -1, 0, 1, -1, 1]]
print(hafnian(M))
13
M = [[-1, 1, 0, 1, 0, -1, 0, 0, -1, 1, -1, 1, 0, -1], [1, -1, 1, -1, 1, 1, -1, 0, -1, 1, 1, 0, 0, -1], [0, 1, 1, 1, -1, 1, -1, -1, 0, 0, -1, 0, -1, -1], [1, -1, 1, -1, 1, 0, 1, 1, -1, -1, 0, 0, 1, 1], [0, 1, -1, 1, 0, 1, 0, 1, -1, -1, 1, 1, 0, -1], [-1, 1, 1, 0, 1, 1, -1, 0, 1, -1, -1, -1, 1, -1], [0, -1, -1, 1, 0, -1, -1, -1, 0, 1, -1, 0, 1, -1], [0, 0, -1, 1, 1, 0, -1, 0, 0, -1, 0, 0, 0, 1], [-1, -1, 0, -1, -1, 1, 0, 0, 1, 1, 0, 1, -1, 0], [1, 1, 0, -1, -1, -1, 1, -1, 1, 1, 1, 0, 1, 0], [-1, 1, -1, 0, 1, -1, -1, 0, 0, 1, -1, 0, -1, 0], [1, 0, 0, 0, 1, -1, 0, 0, 1, 0, 0, 1, 1, 1], [0, 0, -1, 1, 0, 1, 1, 0, -1, 1, -1, 1, 1, -1], [-1, -1, -1, 1, -1, -1, -1, 1, 0, 0, 0, 1, -1, -1]]
print(hafnian(M))
83
งาน
คุณควรเขียนโค้ดที่ได้รับ2n
จาก2n
เมทริกซ์ผลลัพธ์ของ Hafnian
เนื่องจากฉันจะต้องทดสอบโค้ดของคุณมันจะมีประโยชน์ถ้าคุณสามารถให้วิธีที่ง่ายสำหรับฉันในการให้เมทริกซ์เป็นข้อมูลเข้ากับโค้ดของคุณเช่นโดยการอ่านจากมาตรฐานในฉันจะทดสอบโค้ดของคุณในเมทริกซ์ที่สุ่มเลือกด้วยองค์ประกอบ เลือกจาก {-1, 0, 1} จุดประสงค์ของการทดสอบเช่นนี้คือเพื่อลดโอกาสที่ Hafnian จะมีค่ามาก
นึกคิดรหัสของคุณจะสามารถอ่านในเมทริกซ์ตรงที่ฉันมีพวกเขาในตัวอย่างในคำถามนี้ตรงจากมาตรฐานมานั่นคือการป้อนข้อมูลจะมีลักษณะ[[1,-1],[-1,-1]]
เช่น หากคุณต้องการใช้รูปแบบการป้อนข้อมูลอื่นโปรดถามและฉันจะพยายามอย่างดีที่สุดเพื่อรองรับ
คะแนนและความสัมพันธ์
ฉันจะทดสอบโค้ดของคุณในเมทริกซ์แบบสุ่มที่เพิ่มขนาดและหยุดในครั้งแรกที่รหัสของคุณใช้เวลามากกว่า 1 นาทีบนคอมพิวเตอร์ของฉัน เมทริกซ์การให้คะแนนจะสอดคล้องกันสำหรับการส่งทั้งหมดเพื่อความเป็นธรรม
หากคนสองคนได้คะแนนเท่ากันผู้ชนะคือคนที่เร็วที่สุดสำหรับค่าn
นั้น หากสิ่งนั้นอยู่ภายใน 1 วินาทีของกันและกันมันก็จะเป็นโพสต์ก่อน
ภาษาและห้องสมุด
คุณสามารถใช้ภาษาและไลบรารีใด ๆ ที่คุณต้องการ แต่ไม่มีฟังก์ชั่นที่มีอยู่แล้วในการคำนวณ Hafnian หากเป็นไปได้มันจะเป็นการดีที่จะสามารถรันโค้ดของคุณได้ดังนั้นโปรดระบุคำอธิบายโดยละเอียดเกี่ยวกับวิธีการรัน / คอมไพล์โค้ดของคุณใน Linux หากเป็นไปได้ "
My Machineการจับเวลาจะทำงานบนเครื่อง 64 บิตของฉัน นี่คือการติดตั้ง Ubuntu มาตรฐานกับ 8GB RAM, AMD FX-8350 Eight-Core Processor และ Radeon HD 4250 นี่หมายความว่าฉันต้องสามารถเรียกใช้รหัสของคุณได้
สอบถามคำตอบได้หลายภาษา
มันจะเป็นการดีหากได้รับคำตอบในภาษาการเขียนโปรแกรมที่รวดเร็วเป็นพิเศษที่คุณชื่นชอบ ในการเริ่มต้นสิ่งปิดวิธีการเกี่ยวกับFortran , nimและสนิม ?
ลีดเดอร์บอร์ด
- 52โดยไมล์โดยใช้ภาษา C ++ 30 วินาที.
- 50โดย NGN โดยใช้C 50 วินาที
- 46คริสเตียน Sievers ใช้Haskell 40 วินาที
- 40โดยใช้ไมล์งูหลาม 2 + pypy 41 วินาที
- 34โดย NGN ใช้งูหลาม 3 + pypy 29 วินาที
- 28โดยเดนนิสใช้งูหลาม 3 35 วินาที (Pypy ช้ากว่า)