// OBI 2023 - Fase 2 // Startup - Solução O(N + A) com manipulação de listas e vetores // Mateus Bezrutchka // #include #include #include using namespace std; const int MAXN = 100100; int n, a; int chefe[MAXN]; int salario[MAXN]; vector subordinados[MAXN]; // conta quantos subordinados diretos tem salário maior que ele no momento int insat_cnt[MAXN]; int insatisfacao_atual; // mantém a resposta // Chamada no máximo 2 vezes (início e ajuste dele) para cada i void calc_insat_cnt(int i) { insat_cnt[i] = 0; for (int k = 0; k < subordinados[i].size(); k++) { int j = subordinados[i][k]; if (salario[j] > salario[i]) { insat_cnt[i]++; } } } void calc_insatisfacao_inicial() { for (int i = 2; i <= n; i++) { subordinados[chefe[i]].push_back(i); } insatisfacao_atual = 0; for (int i = 1; i <= n; i++) { calc_insat_cnt(i); if (insat_cnt[i] > 0) { insatisfacao_atual++; } } } // apenas duas pessoas podem ter sido afetadas pela // mudança atual: o próprio funcionario i, e o chefe dele void atualiza_salario(int i, int val) { // atualiza contador do chefe if (i != 1) { int c = chefe[i]; if (salario[i] <= salario[c] && val > salario[c]) { insat_cnt[c]++; if (insat_cnt[c] == 1) insatisfacao_atual++; // acabou de ficar insatisfeito } else if (salario[i] > salario[c] && val <= salario[c]) { insat_cnt[c]--; if (insat_cnt[c] == 0) insatisfacao_atual--; // acabou de ficar satisfeito } } salario[i] = val; // atualiza contador do i int old_cnt = insat_cnt[i]; calc_insat_cnt(i); int new_cnt = insat_cnt[i]; if (old_cnt == 0 && new_cnt > 0) { insatisfacao_atual++; } else if (old_cnt > 0 && new_cnt == 0) { insatisfacao_atual--; } } int main() { scanf("%d", &n); for (int i = 1; i <= n; i++) { scanf("%d %d", &chefe[i], &salario[i]); } calc_insatisfacao_inicial(); printf("%d\n", insatisfacao_atual); scanf("%d", &a); while (a--) { int funcionario, novo_salario; scanf("%d %d", &funcionario, &novo_salario); atualiza_salario(funcionario, novo_salario); printf("%d\n", insatisfacao_atual); } return 0; }