题意:
规则:
五张牌均严格小于5,五张牌的和小于等于10,得60分。
五张牌都是$J,Q,K$,得50分。
五张牌有四张牌相同,得40分。
如果其中三张牌的和是10的倍数,并且其他两张牌的和是10的倍数,得30分
如果其中三张牌的和是10的倍数,并且其他两张牌的和对于10的余数大于等于7,得$2*$其他两张牌的和对于10的余数
如果其中三张牌的和是10的倍数,并且其他两张牌的和对于10的余数大于等于7,得其他两张牌的和对于10的余数
其余情况不得分,同时每次只能获取最高分。
现在你手上已经有四张牌,求拿到第五张牌后的分数期望(四舍五入)
思路:
预处理出所有情况,最后遍历一次得到总分后除以13
#include<bits/stdc++.h> using namespace std; typedef long long ll; const ll MOD = 1e9 + 7; int ans[20][20][20][20][20]; void Init() { for (int a = 1; a <= 13; ++a) { for (int b = 1; b <= 13; ++b) { for (int c = 1; c <= 13; ++c) { for (int d = 1; d <= 13; ++d) { for (int e = 1; e <= 13; ++e) { if (a < 5 && b < 5 && c < 5 && d < 5 && e < 5 && a + b + c + d + e <= 10) { ans[a][b][c][d][e] = 60; } else if (a >= 11 && b >= 11 && c >= 11 && d >= 11 && e >= 11) { ans[a][b][c][d][e] = 50; } else if ((a == b && b == c && c == d) || (a == b && b == c && c == e) || (a == b && b == d && d == e) || (a == c && c == d && d == e) || (b == c && c == d && d == e)) { ans[a][b][c][d][e] = 40; } else { if ((min(10, a) + min(10, b) + min(10, c)) % 10 == 0 || (min(10, a) + min(10, b) + min(10, d)) % 10 == 0 || (min(10, a) + min(10, b) + min(10, e)) % 10 == 0 || (min(10, a) + min(10, c) + min(10, d)) % 10 == 0 || (min(10, a) + min(10, c) + min(10, e)) % 10 == 0 || (min(10, a) + min(10, d) + min(10, e)) % 10 == 0 || (min(10, b) + min(10, c) + min(10, d)) % 10 == 0 || (min(10, b) + min(10, c) + min(10, e)) % 10 == 0 || (min(10, b) + min(10, d) + min(10, e)) % 10 == 0 || (min(10, b) + min(10, d) + min(10, e)) % 10 == 0 || (min(10, c) + min(10, d) + min(10, e)) % 10 == 0) { int sum = min(10, a) + min(10, b) + min(10, c) + min(10, d) + min(10, e); if (sum % 10 == 0) ans[a][b][c][d][e] = 30; else if (sum % 10 >= 7) ans[a][b][c][d][e] = 2 * (sum % 10); else ans[a][b][c][d][e] = sum % 10; } } } } } } } } void RUN() { Init(); int t; scanf("%d", &t); while (t--) { int a, b, c, d; scanf("%d %d %d %d", &a, &b, &c, &d); int sum = 0; for (int i = 1; i <= 13; ++i) sum += ans[a][b][c][d][i]; sum = (sum / 13.0) + 0.5; printf("%d\n", sum); } } int main() { #ifdef LOCAL_JUDGE freopen("Text.txt", "r", stdin); #endif // LOCAL_JUDGE RUN(); #ifdef LOCAL_JUDGE fclose(stdin); #endif // LOCAL_JUDGE return 0; }
枚举最后一张牌,求总分,最后除以13
#include<bits/stdc++.h> using namespace std; int a[10], b[10]; int c[15]; void RUN() { int t; scanf("%d", &t); while (t--) { for (int i = 1; i <= 4; ++i) scanf("%d", a + i); b[1] = min(10, a[1]) + min(10, a[2]); b[2] = min(10, a[1]) + min(10, a[3]); b[3] = min(10, a[1]) + min(10, a[4]); b[4] = min(10, a[2]) + min(10, a[3]); b[5] = min(10, a[2]) + min(10, a[4]); b[6] = min(10, a[3]) + min(10, a[4]); b[7] = 0; int tmp = 0; for (int i = 1; i <= 4; ++i) tmp += min(10, a[i]); for (int i = 1; i <= 4; ++i) { if ((tmp - min(10, a[i])) % 10 == 0) { b[7] = 1; break; } } double ans = 0; for (int i = 1; i <= 13; ++i) { a[5] = i; //1 if (a[1] < 5 && a[2] < 5 && a[3] < 5 && a[4] < 5 && a[5] < 5 && a[1] + a[2] + a[3] + a[4] + a[5] <= 10) { ans += 60.0; continue; } //2 if (a[1] >= 11 && a[2] >= 11 && a[3] >= 11 && a[4] >= 11 && a[5] >= 11) { ans += 50.0; continue; } //3 if ((a[1] == a[2] && a[2] == a[3] && a[3] == a[4]) || (a[1] == a[2] && a[2] == a[3] && a[3] == a[5]) || (a[1] == a[2] && a[2] == a[4] && a[4] == a[5]) || (a[1] == a[3] && a[3] == a[4] && a[4] == a[5]) || (a[2] == a[3] && a[3] == a[4] && a[4] == a[5])) { ans += 40.0; continue; } //4 int sum = 0; for (int i = 1; i <= 5; ++i) sum += min(10, a[i]); if (b[7]) { if (sum % 10 == 0) ans += 30.0; else if (sum % 10 >= 7) ans += 2.0 * (sum % 10); else ans += sum % 10; continue; } //5 int res = -1; for (int j = 1; j <= 6; ++j) { if ((b[j] + min(10, a[5])) % 10 == 0) { res = sum % 10; break; } } if (res == -1) continue; if (res == 0) ans += 30.0; else if (res >= 7) ans += 2.0 * res; else if (res != -1) ans += res; } ans = (ans / 13.0) + 0.5; printf("%d\n", (int)ans); } } int main() { #ifdef LOCAL_JUDGE freopen("Text.txt", "r", stdin); #endif // LOCAL_JUDGE RUN(); #ifdef LOCAL_JUDGE fclose(stdin); #endif // LOCAL_JUDGE return 0; }
比赛的时候写丑了,同时对于题意理解不明确?(说好的一副牌呢!)