Pular para o conteúdo principal

Questão de Programação — C — Avança SP 2025

ProgramaçãoC
Código
qg415718
Banca
Avança SP
Órgão
Prefeitura de Caconde - SP
Ano
2025
Nível
Médio
Cargo
Técnico em Informática
Esta instrução obtém o bloqueio de exclusão mútua para um determinado objeto, executa um bloco de instruções e, em seguida, libera o bloqueio. No C#, qual palavra-chave garante que um bloco de código seja executado por apenas uma thread por vez?
  1. Alock
  2. Bvolatile
  3. Casync
  4. Dawait
  5. Eyield
Revelar gabarito e comentário

GabaritoA — lock

Comentário gerado por IA. É um apoio ao estudo, ancorado em fontes, mas pode conter imprecisões — confira sempre na fonte oficial (lei, súmula, edital e gabarito da banca). Encontrou um erro? Use “Reportar”.

Exclusão mútua em C#: a palavra-chave lock

Gabarito: letra A. A palavra-chave lock do C# é exatamente o mecanismo que obtém o bloqueio de exclusão mútua sobre um objeto, executa o bloco de código e libera o bloqueio ao final, garantindo que apenas uma thread por vez execute aquela seção crítica. As demais alternativas (volatile, async, await, yield) têm funções completamente diferentes na linguagem, como veremos.

O conceito central aqui é o de exclusão mútua e seção crítica. Quando múltiplas threads acessam e modificam um mesmo recurso compartilhado (uma variável, uma lista, um arquivo), pode ocorrer uma condição de corrida (race condition), em que o resultado final depende da ordem imprevisível de execução das threads. Para evitar isso, é preciso garantir que apenas uma thread por vez entre na região que manipula o recurso — essa região é a seção crítica. O lock do C# é a forma mais simples e direta de implementar essa proteção: ele recebe um objeto como argumento (o lock object), tenta adquirir o bloqueio exclusivo sobre ele e, se conseguir, executa o bloco; ao sair do bloco (normalmente ou por exceção), o bloqueio é liberado automaticamente. Internamente, o lock é equivalente a usar Monitor.Enter e Monitor.Exit com um bloco try/finally, garantindo a liberação mesmo em caso de erro.

Na prática, o uso típico é:

private readonly object _lockObj = new object();

public void MetodoSeguro()
{
    lock (_lockObj)
    {
        // seção crítica: apenas uma thread por vez executa este trecho
    }
}

O objeto usado no lock serve como identificador do bloqueio: todas as threads que usarem o mesmo objeto para lock competem entre si; se usarem objetos diferentes, não há exclusão mútua entre elas. Por isso, a prática recomendada é usar um objeto privado dedicado, nunca this ou um tipo público, para evitar bloqueios indevidos.

A distinção que importa nesta questão é entre lock e as outras palavras-chave: volatile é um modificador que informa ao compilador que o campo pode ser alterado por múltiplas threads e que a leitura/escrita deve ser atômica e visível imediatamente — mas não cria exclusão mútua nem impede que duas threads entrem simultaneamente em um bloco. async e await são usados para programação assíncrona, permitindo que uma operação que demora (como I/O) não bloqueie a thread, mas não têm relação com exclusão mútua. yield é usado em iteradores para produzir uma sequência de valores, também sem relação com concorrência.

A pegadinha que a banca explora aqui é justamente a confusão entre sincronização de acesso (lock) e visibilidade de memória (volatile). O candidato que sabe que volatile tem algo a ver com threads pode marcá-lo, mas ele não garante que apenas uma thread execute um bloco — ele apenas garante que o valor da variável seja lido da memória principal, não de um cache local. A exclusão mútua é o papel do lock.

Guarde a fronteira: lock = exclusão mútua (uma thread por vez); volatile = visibilidade (leitura/escrita atômica, sem cache). É exatamente nessa fronteira que as alternativas se dividem.

Palavras-chave de concorrência em C#
  • 1lock
    • Exclusão mútua (uma thread por vez)
    • Libera o bloqueio ao final
  • 2volatile
    • Visibilidade de memória (sem cache)
    • Não impede acesso simultâneo
  • 3async / await
    • Programação assíncrona
    • Sem relação com exclusão mútua
  • 4yield
    • Iteradores (lazy evaluation)
    • Sem relação com concorrência
LEVEL · soulevel.com.br

Alternativa A — ✅ Correta ⟵ GABARITO

A palavra-chave lock é a resposta. Ela implementa exatamente o comportamento descrito no enunciado: obtém o bloqueio de exclusão mútua sobre um objeto, executa o bloco de instruções e libera o bloqueio ao final. É o mecanismo padrão do C# para proteger seções críticas contra acesso concorrente.

Alternativa B — ❌ Incorreta

volatile é um modificador de campo que garante que leituras e escritas sejam feitas diretamente na memória principal, sem cache local da thread. Ele não impede que duas threads executem o mesmo bloco simultaneamente — não há exclusão mútua. A confusão é comum porque volatile também é usado em cenários multithread, mas com finalidade distinta: visibilidade, não exclusão.

Alternativa C — ❌ Incorreta

async é um modificador que marca um método como assíncrono, permitindo que ele use await para liberar a thread durante operações de longa duração. Não tem qualquer relação com exclusão mútua ou bloqueio de threads.

Alternativa D — ❌ Incorreta

await é usado dentro de métodos async para aguardar a conclusão de uma operação assíncrona sem bloquear a thread. Também não tem relação com exclusão mútua.

Alternativa E — ❌ Incorreta

yield é usado em iteradores para retornar uma sequência de valores sob demanda (lazy evaluation). Não tem relação com concorrência ou exclusão mútua.

NÃO CAIA NESSA!

A banca explora a confusão entre lock e volatile. Ambos aparecem em contextos de multithreading, mas volatile apenas garante visibilidade de memória — não impede que duas threads entrem no mesmo bloco. Se a alternativa pede "apenas uma thread por vez", a resposta é sempre lock (ou Monitor), nunca volatile.

PEGA ESSA DICA!

Para fixar, lembre-se: lock = portaria com segurança (um de cada vez); volatile = outdoor atualizado (todo mundo vê o valor novo). Quando a questão falar em "exclusão mútua", "seção crítica", "uma thread por vez", marque lock sem hesitar.

Gabarito: letra A

Link permanente: /questoes/qg415718