QOJ.ac

QOJ

Süre Sınırı: 1 s Bellek Sınırı: 256 MB Toplam puan: 100 Zorluk: [göster] Etkileşimli

#51. Popa

İstatistikler

“그는 무법자이고 이름난 자라네, 용감한 Andrii Popa.

밤낮으로 말을 달리며, 큰길에서 통행세를 거두니 온 나라 어디에서나 도둑잡이들이 죽을힘을 다해 도망치네”

— “Andrii Popa”, Phoenix

Ghiță에게는 $N$개의 양의 정수 가중치로 이루어진 $0$-기반 수열 $S$가 있습니다. 그는 카르파티아 산맥의 왕이므로, 정점들의 번호가 $0, 1, \ldots, N - 1$이고 다음 조건을 만족하는 이진 트리를 구성하고자 합니다:

  • 트리의 중위 순회(inorder traversal) 결과는 정점들을 번호가 증가하는 순서대로 나열한 것이다. 이진 트리의 중위 순회는 루트의 왼쪽 자식을 루트로 하는 서브트리의 중위 순회(왼쪽 자식이 존재하는 경우), 그 다음 루트의 번호, 그 다음 루트의 오른쪽 자식을 루트로 하는 서브트리의 중위 순회(오른쪽 자식이 존재하는 경우)로 이루어진다.
  • 정점 $x$가 정점 $y$의 부모이면 $S_x$는 $S_y$의 약수이다.

이진 트리란 각 정점이 최대 두 개의 자식을 가지며, 이들을 각각 왼쪽 자식과 오른쪽 자식이라고 부르는 트리 자료구조임을 상기합시다.

불행히도 유명한 무법자 Andrii Popa가 수열 $S$를 훔쳐 갔기 때문에, Ghiță는 더 이상 수열에 직접 접근할 수 없습니다. 첨단 기술(그의 휴대전화)을 사용하면, 그는 $S$의 임의의 두 연속 부분 수열 $[a, b]$와 $[c, d]$에 대해 $\gcd[a, b]$와 $\gcd[c, d]$가 같은지 알아낼 수 있습니다. 여기서 $\gcd[x, y]$는 $S_x, S_{x+1}, S_{x+2}, \ldots, S_y$의 최대공약수입니다. 안타깝게도 이 기술은 꽤 비싸서, Ghiță가 이를 $Q$번 초과하여 사용하면 거액의 벌금을 내야 합니다. 이 기술을 최대 $Q$번 사용하여 원하는 트리를 구성할 수 있도록 그를 도와주십시오. 이것이 항상 가능함이 보장됩니다. 올바른 해라면 어떤 것이든 정답으로 인정됩니다.

인터랙션

참가자는 헤더 popa.h(C / C++)를 포함하거나 popa.pas(Pascal)를 구현해야 합니다. 참가자는 다음 함수를 구현해야 합니다:

int solve(int N, int* Left, int* Right);
function solve(N: LongInt, var Left, Right: array of LongInt): LongInt;

이 함수는 트리의 루트를 반환해야 하며, $\text{Left}_i$와 $\text{Right}_i$를 각각 정점 $i$의 왼쪽 자식과 오른쪽 자식으로 설정해야 합니다. 정점 $i$에 왼쪽 자식이 없다면 $\text{Left}_i$는 $-1$이어야 합니다. 정점 $i$에 오른쪽 자식이 없다면 $\text{Right}_i$는 $-1$이어야 합니다. Left와 Right는 이미 할당된 크기가 정확히 $N$인 두 배열을 가리킵니다.

solve 함수는 한 번의 실행 동안 최대 $5$번 호출될 수 있습니다. 전역 변수 사용에 주의할 것을 권장합니다.

참가자는 다음 함수를 사용할 수 있습니다:

int query(int a, int b, int c, int d);
function query(a, b, c, d: LongInt): LongInt;

이 함수는 $0 \le a \le b < N$이고 $0 \le c \le d < N$일 때, $\gcd[a, b]$가 $\gcd[c, d]$와 같으면 $1$을 반환하고, 그렇지 않으면 $0$을 반환합니다.

서브태스크

서브태스크 1 (37점)

  • $N = 100$
  • $Q = 10000$

서브태스크 2 (24점)

  • $N = 1000$
  • $Q = 20000$

서브태스크 3 (39점)

  • $N = 1000$
  • $Q = 2000$

예제

$S = [12, 4, 16, 2, 2, 20]$에 대한 인터랙션의 예시는 다음과 같습니다:

solve 호출 query 호출 solve 호출 이후
solve(6, Left, Right)
query(0, 1, 3, 5) → $0$ 반환
query(4, 5, 1, 3) → $1$ 반환
solve → $3$ 반환; Left는 [-1, 0, -1, 1, -1, -1]을 가리킴; Right는 [-1, 2, -1, 4, 5, -1]을 가리킴

참고

앞선 예제에 대해 Ghiță가 원하는 종류의 트리 중 하나는 다음과 같습니다:

problem_51_9045a83d122fa86162a3e40ade701483.png

Discussions

About Discussions

The discussion section is only for posting: General Discussions (problem-solving strategies, alternative approaches), and Off-topic conversations.

This is NOT for reporting issues! If you want to report bugs or errors, please use the Issues section below.

Open Discussions 0
No discussions in this category.

Issues

About Issues

If you find any issues with the problem (statement, scoring, time/memory limits, test cases, etc.), you may submit an issue here. A problem moderator will review your issue.

Guidelines:

  1. This is not a place to publish discussions, editorials, or requests to debug your code. Issues are only visible to you and problem moderators.
  2. Do not submit duplicated issues.
  3. Issues must be filed in English or Chinese only.
Active Issues 0
No issues in this category.
Closed/Resolved Issues 0
No issues in this category.