#P16457. [UOI 2026] Guess the Number

    ID: 18841 远端评测题 1000ms 512MiB 尝试: 0 已通过: 0 显示难度提高+/省选− 上传者: 标签>二分交互题Special Judge2026UOI(乌克兰)

[UOI 2026] Guess the Number

题目描述

有一个隐藏的整数 nn (1≤n<1081 \le n < 10^8),且 nn 不被 1010 整除。你的任务是找出这个数。

你可以提出如下形式的询问:选择一个整数 xx (1≤x≤1091 \le x \le 10^9)。作为回答,你将得到数 n⋅xn \cdot x 的首位数字。

一个正整数的首位数字是指其十进制表示中最靠左的那一位数字。例如,数 77、4242、123456123456 的首位数字分别是 77、44、11。

你需要找出隐藏的整数 nn。对于每个测试用例,你至多可以使用 2828 次询问。

输入格式

第一行包含两个整数 tt 和 qq (1≤t≤103,q=281 \le t \le 10^3, q=28) —— 测试用例的数量以及每个测试用例中允许使用的最大询问次数。

交互方式

在每个测试用例中,都隐藏着一个独立的数 nn。

若要发起询问,请输出 $$\texttt{? } x$$,其中 1≤x≤1091 \le x \le 10^9。

作为对询问的回应,裁判程序会输出一个整数 dd (1≤d≤91 \le d \le 9) —— 数 n⋅xn \cdot x 的首位数字。

在输出询问后,请不要忘记输出一个换行符并刷新输出缓冲区。否则,你将收到 Time limit exceeded\tt{Time\ limit\ exceeded}(超出时间限制)的判决。要刷新缓冲区,请使用:

  • C++ 中的 fflush(stdout)\tt{fflush(stdout)} 或 cout.flush()\tt{cout.flush()};
  • Java 中的 System.out.flush()\tt{System.out.flush()};
  • Pascal 中的 flush(output)\tt{flush(output)};
  • Python 中的 stdout.flush()\tt{stdout.flush()}。

当你确定隐藏的数 nn 后,请输出 $$\texttt{! } n$$。

在此之后,如果这是最后一个测试用例,你必须终止你的程序。否则,你应当继续与下一个测试用例进行交互。

qq 是你的程序在一个测试用例中最多可以使用的 ?\texttt{?} 询问次数。输出形如 !\texttt{!} 的答案不计入询问次数。

请注意,如果你的询问不合法,交互器会输出 -1\texttt{-1} 并终止程序。询问在以下情形下被认为不合法:

  • xx 不满足约束 1≤x≤1091 \le x \le 10^9;
  • 当前测试用例中的询问次数超过了 qq;
  • 答案 ! n\texttt{! } n 不正确。

如果你读到了 -1\texttt{-1},请立即终止你的程序,以便收到 Wrong answer\tt{Wrong\ answer}(答案错误)的判决,而非其他不可预期的判决。

1 28
1
6
? 1
? 59
! 11

提示

考虑这个例子。假设在该例子中额外已知隐藏的数小于 100100。

在询问 x=1x = 1 并得到回答 11 后,我们得知隐藏数的首位数字是 11。

在询问 x=59x = 59 并得到回答 66 后,我们得知隐藏数与 5959 的乘积的首位数字是 66。

在所有小于 100100 且不被 1010 整除的数中,只有 1111 同时满足这两个条件。因此,样例中的答案为 1111。

计分

  • (22 分):n≤10n \le 10;
  • (66 分):n≤100n \le 100;
  • (77 分):n≤1000n \le 1000;
  • (88 分):n≤10000n \le 10000;
  • (1010 分):nn 是完全平方数;
  • (1010 分):n≤105n \le 10^5;
  • (1111 分):n≤106n \le 10^6;
  • (1212 分):n≤107n \le 10^7;
  • (1414 分):n≤5⋅107n \le 5 \cdot 10^7;
  • (2020 分):无额外限制。

一个解答仅当对其所属子任务中的每一个测试用例,都能在不超过 qq 次询问的条件下正确找出数 nn,才算通过该子任务。

翻译由 DeepSeek V4 Pro 完成