結果
| 問題 | No.3510 RPS Eliminations |
| コンテスト | |
| ユーザー |
|
| 提出日時 | 2026-03-18 14:02:02 |
| 言語 | PyPy3 (7.3.17) |
| 結果 |
RE
(最新)
AC
(最初)
|
| 実行時間 | - |
| コード長 | 3,592 bytes |
| 記録 | |
| コンパイル時間 | 459 ms |
| コンパイル使用メモリ | 85,120 KB |
| 実行使用メモリ | 97,152 KB |
| 最終ジャッジ日時 | 2026-04-17 19:42:04 |
| 合計ジャッジ時間 | 4,601 ms |
|
ジャッジサーバーID (参考情報) |
judge1_1 / judge2_0 |
(要ログイン)
| ファイルパターン | 結果 |
|---|---|
| sample | RE * 1 |
| other | WA * 16 RE * 12 |
ソースコード
# gemini 3.1pro テスト
import sys
def solve():
# 入力の読み込み
input = sys.stdin.read
data = input().split()
if not data:
return
N = int(data[0])
A = [int(x) for x in data[1:]]
# 1. BITを用いた二分木の構築
tree = [0] * (N + 1)
for i in range(1, N + 1):
tree[i] = i & (-i)
def add(i, delta):
while i <= N:
tree[i] += delta
i += i & (-i)
def get_kth(k):
idx = 0
for i in range(N.bit_length(), -1, -1):
next_idx = idx + (1 << i)
if next_idx <= N and tree[next_idx] < k:
idx = next_idx
k -= tree[idx]
return idx + 1
left_child = [0] * (2 * N)
right_child = [0] * (2 * N)
node_at_index = list(range(N + 1))
for i in range(1, N):
a_i = A[i - 1]
idx1 = get_kth(a_i)
idx2 = get_kth(a_i + 1)
u = node_at_index[idx1]
v = node_at_index[idx2]
new_node = N + i
left_child[new_node] = u
right_child[new_node] = v
# マージ(idx2を削除し、idx1の指す先を親ノードに更新)
node_at_index[idx1] = new_node
add(idx2, -1)
# 2. ボトムアップDPの準備
# rank_val[u][c] : ノードuで文字cを作るときの、候補間の辞書順ランク(0,1,2)
rank_val = [[0] * 3 for _ in range(2 * N)]
choice = [[(0, 0)] * 3 for _ in range(2 * N)]
# 文字の割り当て: R=0, P=1, S=2
# 葉の初期化(辞書順は P < R < S)
for i in range(1, N + 1):
rank_val[i][1] = 0 # Pが0位
rank_val[i][0] = 1 # Rが1位
rank_val[i][2] = 2 # Sが2位
def get_lose(c):
return (c + 2) % 3
# ボトムアップにランクと最適な子の組み合わせを計算
for u in range(N + 1, 2 * N):
L = left_child[u]
R = right_child[u]
for c in range(3):
c1 = c
c2 = get_lose(c)
# 左側にcを置く場合と、左側にcに負ける文字を置く場合を比較
if rank_val[L][c1] < rank_val[L][c2]:
choice[u][c] = (c1, c2)
else:
choice[u][c] = (c2, c1)
# 現在のノードでの 0, 1, 2 のランクを決定するためのソート用キー作成
keys = []
for c in range(3):
pair = choice[u][c]
# (左部分木のランク, 右部分木のランク, 対象の文字)
keys.append((rank_val[L][pair[0]], rank_val[R][pair[1]], c))
keys.sort()
for i, item in enumerate(keys):
c = item[2]
rank_val[u][c] = i
# 3. トップダウンでの文字列復元と出力
root = 2 * N - 1
chars = ['R', 'P', 'S']
# f(S)=R, f(S)=P, f(S)=S の順に処理(0, 1, 2 の順)
for target_c in range(3):
ans = [0] * (N + 1)
stack = [(root, target_c)]
while stack:
u, c = stack.pop()
if u <= N:
ans[u] = c
else:
L = left_child[u]
R = right_child[u]
c_L, c_R = choice[u][c]
# 深さ優先探索で割り当てを降ろしていく
stack.append((R, c_R))
stack.append((L, c_L))
print("".join(chars[ans[i]] for i in range(1, N + 1)))
if __name__ == '__main__':
solve()