import sys # 再帰深度の上限を緩和(念のため) sys.setrecursionlimit(5000) def main(): # 高速I/O input = sys.stdin.readline try: line = input().strip() if not line: return n = int(line) except ValueError: return s = str(n) length_n = len(s) # 計算用バッファ(0-9の個数) counts = [0] * 10 # 答えを格納するコンテナ(リストにして参照で書き換え可能にする) # Javaの static String minForLen に相当 best_ans = [None] # ----------------------------------------------------- # 内部関数定義 (クロージャとして実装) # ----------------------------------------------------- def solve_recursive(idx, tight, current_counts, target_str): if idx == len(target_str): return "" start = int(target_str[idx]) if tight else 0 for d in range(start, 10): if current_counts[d] > 0: current_counts[d] -= 1 next_tight = tight and (d == start) if not next_tight: # 制約が外れた場合(targetより大きい桁を選んだ場合) # 残りは辞書順最小(0から順に詰める)で作る res = [str(d)] for k in range(10): if current_counts[k] > 0: res.append(str(k) * current_counts[k]) current_counts[d] += 1 # backtrack return "".join(res) # 制約が続く場合 res = solve_recursive(idx + 1, next_tight, current_counts, target_str) if res is not None: current_counts[d] += 1 # backtrack return str(d) + res current_counts[d] += 1 # backtrack return None def find_smallest(current_counts, target_str): total_digits = sum(current_counts) if total_digits > len(target_str): # 桁数がtargetより多い場合、最小の非ゼロ数字を先頭にして残りを昇順 for d in range(1, 10): if current_counts[d] > 0: current_counts[d] -= 1 res = [str(d)] for k in range(10): if current_counts[k] > 0: res.append(str(k) * current_counts[k]) current_counts[d] += 1 # backtrack return "".join(res) return None else: # 桁数が同じ場合、target_str以上になる最小の並び替えを探す return solve_recursive(0, True, current_counts, target_str) def check_and_update(cnt, target_str, L): # 高速な妥当性チェック if (L + cnt[0] + cnt[6] + cnt[8]) % 2 != 0: return # Javaロジックのセグメント計算 s0 = cnt[0] + cnt[2] + cnt[3] + cnt[5] + cnt[6] + cnt[7] + cnt[8] + cnt[9] s1 = cnt[0] + cnt[1] + cnt[2] + cnt[3] + cnt[4] + cnt[7] + cnt[8] + cnt[9] s2 = L - cnt[2] s3 = cnt[0] + cnt[2] + cnt[3] + cnt[5] + cnt[6] + cnt[8] + cnt[9] s4 = cnt[0] + cnt[2] + cnt[6] + cnt[8] s5 = cnt[0] + cnt[4] + cnt[5] + cnt[6] + cnt[8] + cnt[9] s6 = cnt[2] + cnt[3] + cnt[4] + cnt[5] + cnt[6] + cnt[8] + cnt[9] base = (s2 + s4) // 2 nine = s3 - base one = base - s4 zero = (s1 - one) - base seven = base - (s5 - zero + one) six = (s0 - zero) - base # 負の値チェック if one < 0 or zero < 0 or seven < 0 or six < 0 or nine < 0: return # 上限チェック if one > cnt[1]: return if zero > cnt[0]: return if seven > cnt[7]: return if six > cnt[6]: return if nine > cnt[9]: return # 整合性チェック if s0 - zero - six != base: return if s1 - one - zero != base: return if s2 - one != base: return if s3 - nine != base: return if s4 + one != base: return if s5 - zero + one + seven != base: return if s6 + zero != base: return # 有効なら最小値を構築 candidate = find_smallest(cnt, target_str) if candidate is not None: if best_ans[0] is None: best_ans[0] = candidate else: # 辞書順比較 (長さ比較含む) if len(candidate) < len(best_ans[0]): best_ans[0] = candidate elif len(candidate) == len(best_ans[0]) and candidate < best_ans[0]: best_ans[0] = candidate def dfs(digit, remaining, current_counts, target_str, L): if digit == 9: current_counts[9] = remaining check_and_update(current_counts, target_str, L) current_counts[9] = 0 # backtrack return for i in range(remaining + 1): current_counts[digit] = i dfs(digit + 1, remaining - i, current_counts, target_str, L) current_counts[digit] = 0 # backtrack # ----------------------------------------------------- # メインループ # ----------------------------------------------------- for l in range(length_n, 21): best_ans[0] = None dfs(0, l, counts, s, l) if best_ans[0] is not None: print(best_ans[0]) break if __name__ == '__main__': main()