Non-transitive dice: Difference between revisions
Content added Content deleted
m (→{{header|Phix}}: minor tidy) |
m (compatibility fix for versions < 1.5) |
||
Line 286: | Line 286: | ||
{{trans|Python}} |
{{trans|Python}} |
||
<lang julia>import Base.>, Base.< |
<lang julia>import Base.>, Base.< |
||
using |
using Combinatorics |
||
struct Die |
struct Die |
||
name::String |
name::String |
||
faces::Vector{Int} |
faces::Vector{Int} |
||
end |
end |
||
""" Compares two die returning 1, -1 or 0 for operators >, < == """ |
""" Compares two die returning 1, -1 or 0 for operators >, < == """ |
||
function cmpd(die1, die2) |
function cmpd(die1, die2) |
||
Line 303: | Line 303: | ||
return (tot[3] > tot[1]) - (tot[1] > tot[3]) |
return (tot[3] > tot[1]) - (tot[1] > tot[3]) |
||
end |
end |
||
Base.:>(d1::Die, d2::Die) = cmpd(d1, d2) == 1 |
Base.:>(d1::Die, d2::Die) = cmpd(d1, d2) == 1 |
||
Base.:<(d1::Die, d2::Die) = cmpd(d1, d2) == -1 |
Base.:<(d1::Die, d2::Die) = cmpd(d1, d2) == -1 |
||
""" True iff ordering of die in dice is non-transitive """ |
""" True iff ordering of die in dice is non-transitive """ |
||
isnontrans(dice) = all(x -> x[1] < x[2], zip(dice, dice[2:end])) && dice[1] > dice[end] |
isnontrans(dice) = length(dice) > 1 && all(x -> x[1] < x[2], zip(dice[2:end-1], dice[2:end])) && dice[1] > dice[end] |
||
findnontrans(alldice, n=3) = [perm for perm in permutations(alldice, n) if isnontrans(perm)] |
findnontrans(alldice, n=3) = [perm for perm in permutations(alldice, n) if isnontrans(perm)] |
||
function possible_dice(sides, mx) |
function possible_dice(sides, mx) |
||
println("\nAll possible 1..$mx $sides-sided dice") |
println("\nAll possible 1..$mx $sides-sided dice") |
||
Line 322: | Line 322: | ||
return uniquedice |
return uniquedice |
||
end |
end |
||
""" Compares two die returning their relationship of their names as a string """ |
""" Compares two die returning their relationship of their names as a string """ |
||
function verbosecmp(die1, die2) |
function verbosecmp(die1, die2) |
||
Line 331: | Line 331: | ||
return win1 > win2 ? "$n1 > $n2" : win1 < win2 ? "$n1 < $n2" : "$n1 = $n2" |
return win1 > win2 ? "$n1 > $n2" : win1 < win2 ? "$n1 < $n2" : "$n1 = $n2" |
||
end |
end |
||
""" Dice cmp function with verbose extra checks """ |
""" Dice cmp function with verbose extra checks """ |
||
function verbosedicecmp(dice) |
function verbosedicecmp(dice) |
||
return join([[verbosecmp(x, y) for (x, y) in zip(dice, dice[2:end])]; |
return join([[verbosecmp(x, y) for (x, y) in zip(dice[1:end-1], dice[2:end])]; |
||
[verbosecmp(dice[1], dice[end])]], ", ") |
[verbosecmp(dice[1], dice[end])]], ", ") |
||
end |
end |
||
function testnontransitivedice(faces) |
function testnontransitivedice(faces) |
||
dice = possible_dice(faces, faces) |
dice = possible_dice(faces, faces) |
||
Line 343: | Line 343: | ||
nontrans = unique(map(x -> sort!(x, lt=(x, y)->x.name<y.name), findnontrans(dice, N))) |
nontrans = unique(map(x -> sort!(x, lt=(x, y)->x.name<y.name), findnontrans(dice, N))) |
||
println("\n Unique sorted non_transitive length-$N combinations found: $(length(nontrans))") |
println("\n Unique sorted non_transitive length-$N combinations found: $(length(nontrans))") |
||
for list in (faces < 5 ? nontrans : [nontrans[end]]) |
for list in (isempty(nontrans) || faces < 5 ? nontrans : [nontrans[end]]) |
||
println(faces < 5 ? "" : " Only printing last example for brevity") |
println(faces < 5 ? "" : " Only printing last example for brevity") |
||
for (i, die) in enumerate(list) |
for (i, die) in enumerate(list) |
||
println(" |
println(" $die$(i < N - 1 ? "," : "]")") |
||
end |
end |
||
end |
end |
||
Line 356: | Line 356: | ||
end |
end |
||
end |
end |
||
@time testnontransitivedice(3) |
@time testnontransitivedice(3) |
||
@time testnontransitivedice(4) |
@time testnontransitivedice(4) |