painhardcore/blazing-rust

Perfilhe e otimize o desempenho em tempo de execução do Rust com benchmarks reproduzíveis. Use sempre que alguém quiser código Rust mais rápido ou mais enxuto (funções lentas, regressões de latência ou throughput, oscilações de alocação, pontos críticos de CPU, stalls assíncronos), mesmo que nada tenha sido medido ainda. A skill mede primeiro e rejeita mudanças sem evidências.

O que é blazing-rust?

Esta skill guia o desenvolvedor na otimização de desempenho de código Rust baseada em evidências, seguindo o princípio de 'medir antes de editar'. Ela define um processo claro: identificar a carga de trabalho, capturar uma linha de base com o perfil de produção otimizado, encontrar gargalos com profiling adequado (CPU, alocações, I/O, stalls assíncronos), formular uma hipótese e fazer uma única alteração mensurável. A skill enfatiza a criação de benchmarks credíveis, separando setup de operação, usando barreiras de otimização como `std::hint::black_box`, e relatando amostras, mediana e variabilidade. O documento também fornece uma tabela prática de 'custo observado vs. mudança candidata', cobrindo desde algoritmos ineficientes e alocações até vetorização e paralelismo, sempre com verificações de corretude. Finalmente, instrui como relatar resultados de forma reprodutível, distinguindo ganhos reais de multithreading de eficiência single-core, e preservando APIs públicas e segurança do código (Safe Rust) em vez de adicionar `unsafe` sem necessidade medida. A skill é ideal para agentes de IA que atuam como engenheiros de desempenho, garantindo que cada mudança seja justificada por dados concretos.

Funciona com~Claude Code~Codex CLI~Cursor
npx skills add https://github.com/painhardcore/blazing-rust/tree/HEAD

Installed? Explore more Programação e Desenvolvimento skills: steipete/bluebubbles, steipete/eightctl, steipete/blucli · View all 6 →

Perguntar na sua IA favorita

Abre um novo chat com esta habilidade de agente já pré-carregada.

Documentação

Rust Turbinado

Melhore o desempenho medido preservando o comportamento. Mantenha a mudança mais simples que produz um ganho reproduzível em entradas representativas.

Meça antes de editar

  1. Identifique a carga de trabalho, a métrica alvo e as restrições de corretude. Leia o caminho crítico e seus chamadores. Respeite a toolchain do projeto, a versão mínima suportada do Rust, as features e os alvos de implantação. Uma solicitação de explicação autoriza medição e perfilamento, não edições.
  2. Capture uma linha de base com o perfil de produção otimizado do projeto, geralmente release. Registre a entrada, o comando exato, a toolchain, as flags, a CPU e o número de threads. Use tamanhos e distribuições de entrada realistas, incluindo casos pequenos e adversos.
  3. Descubra o que limita o desempenho. Faça perfilamento de tempo de CPU, alocações, I/O ou esperas de bloqueio, conforme apropriado. Para stalls assíncronos, inspecione o escalonamento de tarefas e o crescimento de filas com rastreamento ciente do runtime. Use ferramentas existentes primeiro; a seção de perfilamento lista as comuns e como manter símbolos em builds de release. Se o perfilamento não estiver disponível, use medições direcionadas e declare os limites das evidências.
  4. Enuncie uma hipótese e faça uma mudança mensurável. Execute testes de corretude focados e repita o mesmo benchmark. Verifique o resultado na carga de trabalho completa antes de reivindicar uma melhoria perceptível pelo usuário.
  5. Mantenha ganhos suportados. Desfaça apenas suas edições malsucedidas, preservando o trabalho não relacionado. Pare quando a meta for atingida ou quando mudanças adicionais carecerem de evidências.

Torne o benchmark crível

  • Separe a configuração, compilação, geração de entrada e inicialização do processo da operação, a menos que eles pertençam à métrica alvo. Consuma os resultados. Para microbenchmarks, use as barreiras de otimização da biblioteca de benchmarks ou std::hint::black_box nas entradas e saídas. Essas barreiras são de melhor esforço, portanto inspecione resultados implausíveis.
  • Compare trabalho e saídas equivalentes. Mantenha a toolchain, perfil, features, alocador, configurações de CPU e contagem de threads fixos, a menos que um deles seja a variável em teste. Aqueça ao medir estado estacionário. Meça partidas a frio separadamente quando relevante.
  • Repita as execuções e relate o número de amostras, mediana e variabilidade. Alterne execuções de linha de base e candidatas quando a deriva importar. Uma diferença dentro do ruído não estabelece uma vitória.
  • Combine métricas à tarefa. Para serviços, meça latência p95/p99 em uma carga declarada, throughput, erros e uso de recursos. Verifique se a latência reduzida não veio de trabalho descartado ou de uma fila crescente.
  • Reutilize benchmarks existentes. Adicione um pequeno caso de regressão quando uma nova lógica precisar de um. Não instale ferramentas, adicione dependências ou altere configurações de build sem a autorização da tarefa. Nunca invente medições.

Escolha mudanças com base em evidências

Comece com trabalho desnecessário e algoritmos. Considere mudanças de nível mais baixo apenas quando o gargalo restante as exigir. Leia a seção correspondente de o guia de técnicas quando um gargalo medido precisar de mais detalhes.

Custo observadoMudança candidata e verificações
Varreduras ou computação repetidasMelhore o algoritmo ou a escolha da coleção. Remova parsing, ordenação, serialização e buscas duplicados. Considere invalidação de cache e memória se o cache ajudar.
Alocação ou cópiaTome emprestado &str e slices, mova valores ownership, reutilize buffers e reserve capacidades críveis. Tente clone_from ao substituir um valor alocado. Evite coleções intermediárias. clone pode ser barato para handles compartilhados, então meça seu custo.
Buscas em coleçõesUse chaves emprestadas e APIs de entrada onde elas evitam trabalho repetido. Compare vetores densos ou dados ordenados quando o padrão de acesso se adequar. Preserve a resistência a ataques de colisão para chaves não confiáveis ao alterar hashers.
Ordenação ou remoçãoUse select_nth_unstable para seleção, sort_unstable quando a ordem de elementos iguais for irrelevante e sort_by_cached_key para chaves caras. Use swap_remove apenas quando a ordem dos elementos for irrelevante.
Erros de cache ou valores grandesCompare arrays de estruturas com estruturas de arrays. Verifique size_of, align_of e erros de cache. Armazenamento inline pode aumentar a cópia. Considere encaixotar payloads grandes de enums raros, contabilizando alocações e indireção.
Pequenas chamadas ou loops críticosPrefira iteração comum. Ajude o compilador a remover verificações de limites com slices, iteração ou asserções de intervalo. Inspecione o assembly otimizado antes de inlining ou unrolling. Teste entradas vazias, caudas, estouro e tamanho do código.
Busca de textoReutilize regexes compilados e solicite apenas as informações de correspondência necessárias. Compare buscas especializadas de bytes quando a semântica de codificação permitir. Evite reconstruir o estado de busca dentro de loops críticos.
Computação vetorizávelVerifique a autovetorização antes de SIMD explícito. Inspecione o código gerado. Proteja instruções específicas de destino quando necessário e mantenha um fallback escalar. Teste caudas e CPUs representativas. Preserve alinhamento, limites e comportamento numérico.
Trabalho independente de CPUCompare execução serial com paralelismo limitado. Meça custo de escalonamento, contenção, largura de banda, contagem de threads e consumo total de CPU. Ajuste o tamanho da tarefa apenas quando a sobrecarga importar. Preserve semântica de redução.
I/O ou stalls assíncronosReutilize buffers de linha, faça lote de pequenas E/S e trate erros de flush. Preserve latência, manipulação de nova linha e durabilidade. Mantenha trabalho bloqueante ou pesado de CPU fora dos workers assíncronos. Limite concorrência e filas. Preserve ordenação, contrapressão e cancelamento.
Limites de build ou geração de códigoCompare configurações existentes com thin LTO. Teste fat LTO e codegen-units = 1 separadamente antes de combinar. Inclua tempo de build e tamanho do binário. Use flags específicas de CPU apenas quando o hardware de implantação as permitir.

Preserve a corretude

Mantenha APIs públicas, tratamento de erros, validação, ordenação, serialização e contratos FFI intactos. Preserve o comportamento de estouro de inteiros e ponto flutuante. A representação de enum ou a ordem das variantes pode alterar layout e discriminantes; nenhum deles garante uma enum menor ou mais rápida.

Prefira Rust seguro e dependências existentes. Introduzir código inseguro requer uma necessidade medida, invariantes de segurança explícitos e testes focados. Use Miri ou sanitizadores onde suportado e relevante. Nunca troque validação ou solidez por velocidade de benchmark, e não trate testes bem-sucedidos como prova de solidez.

Relate o resultado

Declare o gargalo, a mudança e a decisão de manter ou reverter. Inclua comandos reproduzíveis, resultados antes/depois com variabilidade, figuras relevantes de alocação ou memória, verificações de corretude e trade-offs. Diferencie ganhos de wall-clock multicore de eficiência single-core. Nomeie reivindicações não medidas e plataformas não verificadas.

Habilidades Relacionadas