Giới thiệu
Giả sử bạn và bạn của bạn đang chơi một trò chơi. Bạn của bạn nghĩ về một số chuỗi n
bit cụ thể và nhiệm vụ của bạn là suy ra chuỗi bằng cách đặt câu hỏi cho họ. Tuy nhiên, loại câu hỏi duy nhất bạn được phép hỏi là "Phần tiếp theo phổ biến dài nhất của chuỗi của bạn là bao lâu S
", trong đó S
có bất kỳ chuỗi bit nào. Càng ít câu hỏi bạn cần, càng tốt.
Nhiệm vụ
Nhiệm vụ của bạn là viết một chương trình hoặc hàm lấy đầu vào là một số nguyên dương n
và một chuỗi R
độ dài nhị phân n
. Chuỗi có thể là một mảng các số nguyên, một chuỗi hoặc một số loại hợp lý khác mà bạn chọn. Chương trình của bạn sẽ xuất trình tự R
.
Chương trình của bạn không được phép truy cập chuỗi R
trực tiếp. Điều duy nhất nó được phép làm R
là cung cấp nó làm đầu vào cho hàm len_lcs
cùng với một chuỗi nhị phân khác S
. Hàm len_lcs(R, S)
trả về độ dài của chuỗi con chung dài nhất R
và S
. Điều này có nghĩa là chuỗi bit dài nhất xảy ra như một chuỗi con (không nhất thiết phải liền kề) trong cả hai R
và S
. Các đầu vào trong len_lcs
đó có thể có độ dài khác nhau. Chương trình nên gọi hàm này R
và các chuỗi khác một số lần, và sau đó xây dựng lại chuỗi R
dựa trên thông tin đó.
Thí dụ
Hãy xem xét các đầu vào n = 4
và R = "1010"
. Đầu tiên, chúng tôi có thể đánh giá len_lcs(R, "110")
, đưa ra 3
, vì đây "110"
là chuỗi con chung dài nhất của "1010"
và "110"
. Sau đó, chúng ta biết rằng R
có được từ "110"
bằng cách chèn một bit tại một số vị trí. Tiếp theo, chúng tôi có thể thử len_lcs(R, "0110")
, trả về 3
vì các chuỗi chung dài nhất là "110"
và "010"
, vì vậy "0110"
không chính xác. Sau đó, chúng tôi cố gắng len_lcs(R, "1010")
, mà trở lại 4
. Bây giờ chúng ta biết điều đó R == "1010"
, vì vậy chúng ta có thể trả về chuỗi đó là đầu ra chính xác. Điều này yêu cầu 3 cuộc gọi đến len_lcs
.
Quy tắc và tính điểm
Trong kho lưu trữ này , bạn sẽ tìm thấy một tệp subsequence_data.txt
có chứa 100 chuỗi nhị phân ngẫu nhiên có độ dài trong khoảng từ 75 đến 124. Chúng được tạo bằng cách lấy ba lần thả ngẫu nhiên trong khoảng từ 0 đến 1, lấy trung bình của chúng a
, sau đó lật một lần a
xu xu hướng n
. Điểm số của bạn là số cuộc gọi trung bìnhlen_lcs
trên các chuỗi này, điểm thấp hơn sẽ tốt hơn. Trình của bạn nên ghi lại số lượng cuộc gọi. Không có giới hạn thời gian, ngoại trừ việc bạn nên chạy chương trình của mình trên tệp trước khi gửi.
Trình của bạn sẽ được xác định. PRNG được phép, nhưng họ phải sử dụng ngày hôm nay, 200116
(hoặc tương đương gần nhất), làm hạt giống ngẫu nhiên. Bạn không được phép tối ưu hóa trình của mình đối với các trường hợp thử nghiệm cụ thể này. Nếu tôi nghi ngờ điều này xảy ra, tôi sẽ tạo ra một đợt mới.
Đây không phải là mã golf, vì vậy bạn được khuyến khích viết mã có thể đọc được. Rosetta Code có một trang về chuỗi con chung dài nhất ; bạn có thể sử dụng nó để thực hiện len_lcs
trong ngôn ngữ của bạn lựa chọn.
lcs
thay vì len_lcs
.
lcs(R, "01"*2*n)
trở về R
. ;) Nhưng điều đó có thể hoạt động nếu gọi lcs(R, S)
sẽ tăng điểm len(S)
thay vì 1, hoặc đại loại như thế ...