Xây dựng một chương trình để phân tích các lựa chọn chuỗi lật xu


15

Trong một câu đố trong một cuốn sách cũ của tôi, một trò chơi được xác định trong đó hai người chơi chọn chuỗi các lần lật đồng xu mà họ tin rằng sẽ xuất hiện đầu tiên khi một đồng xu được lật liên tục. (Nó thực sự là những con xúc xắc kỳ quặc và thậm chí, nhưng chi tiết nhỏ này không quan trọng về mặt tương đương vấn đề.)

Cần lưu ý rằng nếu người chơi 1 chọn TTTvà người chơi 2 chọn HTT, thì người chơi 2 có cơ hội chiến thắng 7/8, vì cách duy nhất TTTcó thể đến trước HTTlà nếu ba lần lật đầu tiên đều có đuôi.

Công việc của bạn là tạo ra một chương trình hoặc chức năng sẽ suy ra xác suất rằng một trong hai chuỗi được chọn sẽ đến trước. Chương trình của bạn sẽ lấy hai dòng đầu vào (hoặc hai chuỗi làm đối số), mỗi chuỗi đại diện cho một chuỗi có độ dài 10 hoặc ít hơn:

HTT
TTT

Và đưa ra xác suất người chơi đầu tiên sẽ giành chiến thắng, dưới dạng phân số hoặc số thập phân:

7/8
0.875

Mã ngắn nhất để làm điều này trong bất kỳ ngôn ngữ nào sẽ thắng.


6
Các trình tự luôn luôn có cùng độ dài với nhau?
Uri Granta

1
@UriZarfaty Không, không nhất thiết.
Joe Z.

Mặc dù có lẽ các trình tự phải khác biệt (vì đầu ra không thể chỉ định hòa).
Uri Granta

Vâng, các trình tự phải được phân biệt.
Joe Z.

Cụ thể hơn, một cái không thể là một chuỗi con đầu cuối của cái kia.
Joe Z.

Câu trả lời:


4

Con trăn 3 (139 136 134 132 126 115 143)

Sử dụng thuật toán của Conway như được mô tả tại đây . Xử lý tất cả các cặp chuỗi miễn là lần đầu tiên không phải là kết thúc sau của lần thứ hai (theo hướng dẫn).

def f(a,b):c=lambda x,y=a:sum((x[~i:]==y[:i+1])<<i for i in range(len(x)));return 0 if b in a else(1/(1+(c(a)-c(a,b))/(c(b,b)-c(b))),1)[a in b]

Cảm ơn xnor đã cạo 6 byte. Cảm ơn Zgarb vì đã phát hiện ra một lỗi với các phần sau.


Phiên bản hiện tại không hoạt động với tôi. Đối với đầu vào "HTT""TTT", ocó giá trị -1và nó chia nó cho 0.
Jakube

1
Chơi golf tốt Tôi thích thủ thuật đối số mặc định. Một vài mẹo (chưa được kiểm tra): bạn có thể nhân 2**ivới <<ivà xác suất đầu ra có thể được viết dưới dạng 1/(1/o + 1), trong đó bạn có thể đặt đối ứng otrực tiếp.
xnor

Cảm ơn. Điểm tốt lại o / (1 + o). Hơi xấu hổ vì đã bỏ lỡ <<!
Uri Granta

@Jakube Xin lỗi, không nhận ra bình luận của bạn! Phiên bản hiện tại hoạt động tốt với tôi với "HTT" và "TTT".
Uri Granta

1
Điều này đưa ra một câu trả lời khác cho HTHT, mặc dù người chơi đầu tiên không thể thắng. Câu trả lời khác có cùng một vấn đề.
Zgarb

3

CJam, 44 38 36 byte

Sử dụng cùng một thuật toán của Conway như ở đây .

ll]_m*{~1$,,@f>\f{\#!}2b}/\-:X--Xd\/

Đầu vào là hai chuỗi riêng biệt trong hai dòng. Đầu ra là xác suất chiến thắng đầu tiên trên thứ hai. Các đầu vào không cần phải có cùng độ dài

Tôi đang sử dụng công thức để thắng tỷ lệ cược ( p) cho người chơi đầu tiên A là

nhập mô tả hình ảnh ở đây

Sau đó xác suất được xác định là

nhập mô tả hình ảnh ở đây

mà sau khi đơn giản hóa trở thành

nhập mô tả hình ảnh ở đây

và sau khi đơn giản hóa, trở thành

nhập mô tả hình ảnh ở đây


Ví dụ đầu vào:

HTT
TTT

Đầu ra:

0.875

Dùng thử trực tuyến tại đây


Joe nói trong các bình luận (sau khi điều này được đăng) rằng các chuỗi không nhất thiết phải có cùng độ dài. Tuy nhiên, +1 vì tôi không hiểu CJam.
mdc32

@ mdc32 đã được sửa, giờ dài hơn 1 byte :(
Trình tối ưu hóa

Bạn đã cho tôi tin rằng codegolfSE hiện hỗ trợ LaTeX ... = (
flawr

@flawr HAHA. Xin lỗi về điều đó :(. Đây là các PNG từ trình chỉnh sửa LaTeX trực tuyến.
Trình tối ưu hóa

Điều này đưa ra một câu trả lời khác cho HTHT, mặc dù người chơi đầu tiên không thể thắng. Câu trả lời khác có cùng một vấn đề.
Zgarb

0

Lua 211 190 184

Cũng sử dụng Thuật toán của Conway. Vẫn còn mới với Lua vì vậy điều này có thể được chơi golf chắc chắn hơn.

z=io.read;e=function(s,t)r='';for d in s:gmatch"."do r=r..(d==t:sub(1,1)and 1 or 0);end;return tonumber(r,2);end;a=z();b=z();print((e(a,a)-e(a,b))/(e(b,b)-e(b,a))/(1/((1/2)^b:len())));

Ung dung

z=io.read;
e=function(s,t)
r='';
    for d in s:gmatch"."do 
        r=r..(d==t:sub(1,1)and 1 or 0);
    end;
    return tonumber(r,2);
end;
a=z();
b=z();
print((e(a,a)-e(a,b))/(e(b,b)-e(b,a))/(1/((1/2)^b:len())));

Phiên bản đầu tiên

z=io.read;
e=function(s,t) 
    r=0;
    for d in s:gmatch"."do 
        r=r*10;
        if d==t:sub(1,1)then r=r+1 end;
    end
    return tonumber(r,2);
end;
f=function(n,o)
    return ((e(n,n)-e(n,o))/(e(o,o)-e(o,n)))/(1/((1/2)^3));
end;
print(f(z(),z()));
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.