20 principais conceitos de IA em LLM: explicação detalhada

Este artigo tem um vídeo curto:TikTok

1. Visão geral

Se você é um dev Java começando a integrar LLM (ChatGPT, Gemini, Claude…) em seu sistema, você encontrará muitos termos estranhos: token, embedding, RAG, fine-tuning, hallucination… Este artigo reúne os 20 conceitos de IA mais importantes relacionados a LLM, cada um com uma explicação breve e exemplos práticos (a maioria em Java/Spring AI). Ao terminar, você terá vocabulário suficiente para ler a documentação de API da OpenAI, Anthropic ou projetar um sistema RAG básico.

2. Token e Tokenização

LLM não lê “caracteres” mas lê token — uma unidade menor que a palavra, pode ser uma palavra, parte de uma palavra ou pontuação. Tokenização é o processo de dividir o texto em tokens antes de passar para o modelo.

Entrada:  "Spring Boot é muito poderoso"
Tokens: ["Spring", " Boot", " é", " muito", " poderoso"]  (5 tokens)

O número de tokens determina o custo da chamada de API (cobrança por token) e o limite de comprimento da entrada/saída.

Observação: Textos em português geralmente geram mais tokens que textos em inglês de tamanho similar, então o custo das chamadas de API para conteúdo em português costuma ser maior.

3. Embedding

Embedding é o processo de converter um trecho de texto em um vetor de números reais (por exemplo, 1536 dimensões), de forma que dois textos com significado semelhante tenham vetores próximos. Esta é a base para busca semântica (semantic search).

EmbeddingModel embeddingModel = ...; // bean configurado automaticamente por Spring AI
EmbeddingResponse response = embeddingModel.embedForResponse(
        List.of("Cliente quer cancelar o pedido"));
float[] vector = response.getResult().getOutput();
System.out.println(vector.length); // 1536

embedForResponse chama o modelo de embedding e retorna o vetor. Duas frases como “cancelar pedido” e “cancel order” terão vetores próximos mesmo em idiomas diferentes.

Para comparar a similaridade entre vetores, usamos cosine similarity:

double cosineSimilarity(float[] a, float[] b) {
    double dot = 0, normA = 0, normB = 0;
    for (int i = 0; i < a.length; i++) {
        dot += a[i] * b[i];
        normA += a[i] * a[i];
        normB += b[i] * b[i];
    }
    return dot / (Math.sqrt(normA) * Math.sqrt(normB));
}
@Test
void similarVectorsShouldScoreHigh() {
    float[] a = {1f, 0f, 1f};
    float[] b = {1f, 0.1f, 0.9f};
    assertThat(cosineSimilarity(a, b)).isGreaterThan(0.95);
}

Um valor próximo a 1 significa que dois vetores (e portanto dois textos) têm significado muito semelhante.

4. Context Window

Context window é o número total máximo de tokens que o modelo pode “ver” em uma única chamada — incluindo tanto o prompt quanto a resposta. Ultrapassar esse limite fará o modelo cortar a parte inicial ou retornar um erro.

GPT-4o:        128.000 tokens
Claude 3.5:    200.000 tokens
Gemini 1.5 Pro: 1.000.000 tokens

Para aplicações de chatbot com histórico longo de conversas, você deve ativamente cortar/resumir o histórico antigo antes que a context window fique cheia, caso contrário perderá informações do início da conversa sem aviso claro.

5. Prompt e Prompt Engineering

Prompt é o texto que você envia para o LLM para solicitar que ele faça algo. Prompt engineering é a técnica de projetar prompts para que o modelo responda corretamente e no formato desejado.

Primeiro, adicione a dependência do Spring AI:

<dependency>
    <groupId>org.springframework.ai</groupId>
    <artifactId>spring-ai-openai-spring-boot-starter</artifactId>
    <version>1.0.0</version>
</dependency>
@Service
class OrderSummaryService {
    private final ChatClient chatClient;

    OrderSummaryService(ChatClient.Builder builder) {
        this.chatClient = builder.build();
    }

    String summarize(String orderNote) {
        return chatClient.prompt()
                .user("Resuma o pedido do cliente em 1 frase: " + orderNote)
                .call()
                .content();
    }
}

ChatClient é um wrapper do Spring AI que facilita chamar o modelo sem precisar lidar com HTTP manualmente. .user(...) define o conteúdo do prompt, .call().content() retorna a string resultante.

6. System Prompt vs User Prompt

System prompt é uma instrução “implícita” que define o papel e as regras do modelo durante toda a conversa; user prompt é a pergunta/solicitação específica do usuário.

chatClient.prompt()
        .system("Você é um assistente de atendimento ao cliente de uma loja de sapatos. Sempre responda de forma breve e respeitosa.")
        .user("Quando será entregue meu pedido #1023?")
        .call()
        .content();

O system prompt é definido uma única vez, enquanto o user prompt muda a cada solicitação. Separar esses dois tipos permite controlar a “personalidade” do modelo sem repetir instruções em cada pergunta.

7. Zero-shot, One-shot, Few-shot Learning

Estas são formas de fornecer (ou não fornecer) exemplos no prompt para ensinar o modelo a responder no formato desejado, sem precisar fazer fine-tuning novamente.

Zero-shot: Nenhum exemplo, apenas descrição da tarefa.
Few-shot:  2-5 exemplos entrada -> saída antes de fazer a pergunta real.
String fewShotPrompt = """
    Classifique o sentimento da resenha (positivo/negativo):
    Resenha: "Entrega rápida, qualidade excelente" -> positivo
    Resenha: "Produto com defeito, entrega atrasada 1 semana" -> negativo
    Resenha: "%s" ->
    """.formatted(userReview);

Few-shot geralmente produz resultados mais estáveis que zero-shot para tarefas de classificação/formatação específicas, mas consome mais tokens a cada chamada.

8. Chain-of-Thought (CoT)

CoT é a técnica de pedir ao modelo “pensar passo a passo” antes de dar a resposta final, ajudando a aumentar a precisão em tarefas que requerem raciocínio (matemática, lógica).

chatClient.prompt()
        .user("""
            Um pedido tem 3 produtos custando 120k, 85k, 45k, com desconto de 10%.
            Calcule passo a passo e depois dê o valor total final.
            """)
        .call()
        .content();

Quando pedido para “passo a passo”, o modelo tende a dividir o problema em operações menores, reduzindo a probabilidade de erro comparado a perguntar diretamente “qual é o valor total?”.

9. Temperature e Top-p

Temperature e top-p são dois parâmetros que ajustam o quão “aleatório” é quando o modelo escolhe a próxima palavra. Temperature baixa → respostas consistentes e repetitivas; alta → mais criativo mas pode sair do tópico.

ChatOptions options = OpenAiChatOptions.builder()
        .withTemperature(0.2)
        .withTopP(0.9)
        .build();
temperature = 0.0  -> apropriado para: extração de dados, respostas precisas
temperature = 0.8  -> apropriado para: escrever conteúdo criativo, brainstorming

Observação: Para tarefas que precisam de resultados reproduzíveis (por exemplo, testes automatizados), defina temperature = 0 para reduzir a variação entre chamadas.

10. Attention Mechanism

Attention é o mecanismo que permite o modelo, ao processar uma palavra, “olhar” para todas as outras palavras da frase e calcular automaticamente quais são mais relevantes. É por isso que o modelo consegue entender contexto distante, por exemplo, a que palavra um pronome se refere.

Frase: "O pedido foi cancelado porque o cliente mudou de ideia, ele foi reembolsado."
Attention ajuda o modelo a associar "ele" -> "O pedido", não "cliente".

Você não programa attention diretamente ao usar a API, mas entendê-lo ajuda a explicar por que o modelo às vezes “esquece” do contexto em frases muito distantes ou longas.

11. Transformer Architecture

Transformer é a arquitetura de rede neural que fundamenta praticamente todo LLM atual, usando attention para processar toda a frase simultaneamente (em paralelo) em vez de sequencialmente como RNNs antigas, permitindo treinamento mais rápido em dados enormes.

Tokens de entrada -> Embedding -> [Attention + Feed-Forward] x N camadas -> Probabilidades de saída

O número de camadas (N) e o número de parâmetros decide o “tamanho” do modelo — GPT-4, Claude, Llama são variações do Transformer com números diferentes de camadas e métodos de treinamento.

12. Fine-tuning

Fine-tuning é treinar um modelo já pronto (pretrained) com seus próprios dados, para especializá-lo em uma tarefa específica (por exemplo: responder com o tom de marca correto).

{"messages": [
  {"role": "user", "content": "Quando chega o pedido #203?"},
  {"role": "assistant", "content": "O pedido #203 está a caminho e deve chegar hoje, tudo bem?"}
]}

Este arquivo JSONL é uma linha de dados de treinamento para fine-tuning — cada linha é um exemplo de conversa, você envia milhares de linhas assim para a API de fine-tuning do provedor.

Quando NÃO usar: Se você só precisa que o modelo siga algumas regras simples, prompt engineering ou RAG é muito mais barato e rápido do que fine-tuning.

13. LoRA (Low-Rank Adaptation)

LoRA é uma técnica de fine-tuning econômica: em vez de atualizar todos os bilhões de parâmetros do modelo original, LoRA treina apenas algumas matrizes pequenas “inseridas” nas camadas, mantendo o modelo original congelado.

Modelo original: 7 bilhões de parâmetros (congelado, não muda)
Adaptador LoRA: ~10-50 milhões de parâmetros (é treinado)

Assim, LoRA permite fazer fine-tune de modelos enormes em uma GPU comum, e pode “conectar/desconectar” múltiplos adaptadores diferentes para múltiplos casos de uso usando o mesmo modelo original.

14. Quantization

Quantization é reduzir a precisão numérica dos parâmetros do modelo (por exemplo de float32 para int8/int4) para diminuir o tamanho e acelerar a inferência, sacrificando um pouco de precisão.

FP32: 7B params x 4 bytes = ~28 GB RAM
INT4: 7B params x 0.5 byte = ~3.5 GB RAM

Quantization é a razão pela qual você consegue executar um LLM de 7 bilhões de parâmetros em um laptop comum em vez de precisar de um servidor GPU dedicado — em troca, a qualidade das respostas cai levemente.

15. RAG (Retrieval-Augmented Generation)

RAG é a técnica de combinar busca (retrieval) de dados internos com LLM: antes de responder, o sistema busca os trechos mais relevantes (através de embedding) e os coloca no prompt como “contexto”, ajudando o modelo a responder corretamente com seus dados sem precisar de fine-tuning.

List<Document> relevantDocs = vectorStore.similaritySearch(
        SearchRequest.query("política de troca e devolução").withTopK(3));

String context = relevantDocs.stream()
        .map(Document::getContent)
        .collect(Collectors.joining("\n---\n"));

String answer = chatClient.prompt()
        .system("Responda apenas baseado no contexto fornecido.")
        .user("Contexto:\n" + context + "\n\nPergunta: Posso trocar em quantos dias?")
        .call()
        .content();

similaritySearch busca os 3 documentos mais semelhantes à pergunta, os mescla no prompt e depois envia para o modelo. Assim a resposta segue fielmente a política real da sua empresa, não o conhecimento “genérico” que o modelo aprendeu no treinamento.

16. Vector Database

Vector database é um lugar para armazenar embeddings com metadados, suportando busca de “k vizinhos mais próximos” (k-NN) rápida em milhões de vetores — componente essencial para RAG funcionar em escala (Pinecone, Milvus, PGVector…).

CREATE TABLE documents (
    id SERIAL PRIMARY KEY,
    content TEXT,
    embedding VECTOR(1536)
);

SELECT content FROM documents
ORDER BY embedding <-> '[0.01, -0.02, ...]'
LIMIT 3;

O operador <-> (fornecido pela extensão pgvector) calcula a distância entre o vetor da pergunta e vetores armazenados, retornando os registros mais próximos — este é exatamente o passo similaritySearch da seção 15.

17. Function Calling / Tool Use

Function calling permite que o LLM “solicite” que sua aplicação chame uma função específica (consultar preço, consultar clima, consultar banco de dados) quando ele achar necessário, em vez de inventar dados.

@Tool(description = "Obtém o status do pedido pelo ID")
String getOrderStatus(String orderId) {
    return orderRepository.findStatusById(orderId);
}
chatClient.prompt()
        .user("Qual é o status do pedido #1023?")
        .tools(this)
        .call()
        .content();

Ao enviar a pergunta, o modelo reconhece que precisa chamar getOrderStatus, Spring AI executa a função Java real, obtém o resultado e devolve ao modelo para formular a resposta final — o modelo não precisa mais “adivinhar” o status.

18. AI Agent

Agent é um sistema que usa LLM como “cérebro” para planejar automaticamente, chamar múltiplas ferramentas em sequência, observar resultados e repetir até completar o objetivo — diferente de um chatbot que apenas responde uma vez.

Usuário: "Verifique o pedido #1023, se estiver atrasado mais de 3 dias envie um email de desculpas ao cliente."

Agent executa automaticamente:
1. Chama tool getOrderStatus("1023")
2. Calcula dias de atraso
3. Se > 3 -> chama tool sendEmail(...)
4. Retorna relatório ao usuário

Agents geralmente são construídos com um loop “pensar → agir → observar” (padrão ReAct), combinando múltiplas chamadas de função em sequência para completar uma tarefa com muitas etapas.

19. Hallucination

Hallucination é quando o modelo responde com confiança mas a informação está errada ou completamente inventada — por exemplo, citar uma lei que não existe, ou lembrar de uma API inexistente.

Usuário: "Como funciona a API `OrderService.cancelAndRefund()`?"
Modelo: "Este método reembolsa automaticamente em 24h..." (mas este método não existe no codebase)

A forma mais comum de reduzir hallucination é usar RAG (seção 15) para o modelo se ater ao documento real, e pedir que o modelo responda “eu não sei” quando o contexto não tem informação suficiente, em vez de tentar inferir.

20. Guardrails

Guardrails é um conjunto de camadas de controle (filtrar entrada/saída, validar formato, bloquear conteúdo sensível) ao redor do LLM para garantir que o sistema seja seguro e em conformidade antes de retornar o resultado ao usuário final.

String output = chatClient.prompt().user(userInput).call().content();

if (containsPersonalData(output) || !isValidJson(output)) {
    throw new UnsafeModelOutputException("Saída não atende aos guardrails");
}

Guardrails podem estar na entrada (bloquear prompt injection, conteúdo prejudicial) ou na saída (verificar formato JSON, mascarar números de cartão) — não pule esta etapa ao colocar LLM em produção, mesmo que o modelo “pareça” responder corretamente nos testes.

21. RLHF (Reinforcement Learning from Human Feedback)

RLHF é a técnica de treinar um modelo baseado em feedback humano: humanos classificam várias respostas do modelo, disso treina-se um “modelo de recompensa” para continuar otimizando o modelo original para respostas mais úteis e seguras.

Passo 1: Model gera 3-4 respostas para a mesma pergunta
Passo 2: Humanos classificam: melhor -> pior
Passo 3: Treina-se modelo de recompensa para aprender a "pontuar" como os humanos
Passo 4: Usa-se modelo de recompensa para refinar o LLM via reinforcement learning

RLHF é a razão pela qual ChatGPT, Claude respondem com “tom” respeitoso, recusam solicitações perigosas — diferente do modelo original que apenas “adivinha a próxima palavra” de forma bruta.

22. Conclusão

Os 20 conceitos acima são o vocabulário mínimo para você trabalhar seriamente com LLM: desde o nível baixo (token, embedding, attention) até o nível de aplicação (RAG, function calling, agent, guardrails). Você não precisa entender profundamente a matemática de Transformer para integrar LLM em seu sistema Spring Boot, mas entender corretamente estes conceitos o ajuda a escolher a solução certa — por exemplo, saber quando usar RAG em vez de fine-tuning, quando precisar de guardrails em vez de confiar completamente na saída do modelo.

llmainlpprompt-engineeringspring-ai