Saltar para o conteúdo

Explorar dados num kernel persistente

Este guia mostra-lhe como fazer com que um agente carregue algo dispendioso uma única vez e depois lhe faça várias perguntas, em vez de pagar o carregamento em cada pergunta.

A ferramenta eval executa um interpretador persistente. As variáveis, as importações e os dados carregados sobrevivem entre chamadas.

Um python -c de execução única paga a preparação em cada pergunta. Carregar um dataframe custa segundos e uma centena de megabytes; desenhá-lo num gráfico custa milissegundos. Quando cada pergunta custa o carregamento, um agente faz menos perguntas do que devia — e cada resposta volta como texto que depois tem de voltar a analisar.

Carregue data/runs.csv e diga-me a duração p95 por agente.

import pandas as pd
runs = pd.read_csv("data/runs.csv")
len(runs)

A última expressão é ecoada como num notebook, pelo que len(runs) indica o número de linhas sem um print.

Depois, numa chamada separada:

runs.groupby("agent")["duration_ms"].quantile(0.95).sort_values()

runs continua carregado. Um DataFrame do pandas volta representado como uma tabela, em vez de como um repr.

import matplotlib.pyplot as plt
runs.groupby("agent")["duration_ms"].mean().plot.bar()

As figuras são capturadas depois da célula e devolvidas como imagens, que a transcrição apresenta. Vê o gráfico; o agente também.

As figuras são fechadas após a captura. Uma figura não recolhida seria redesenhada e reenviada também pela próxima célula, pelo que uma sessão de cinco células emitiria o primeiro gráfico cinco vezes.

São reescritas como código simples em vez de darem erro:

O que escreve O que acontece
%pip install x Executa o pip e depois limpa a cache de módulos, para que o próximo import o veja
%cd path os.chdir
!command Um subprocesso capturado
%%bash O resto da célula como um script de shell
%%timeit 1000 execuções cronometradas

A expulsão da cache do %pip é a que importa: instalar num interpretador em execução não faz nada a um módulo já importado, pelo que, sem ela, a versão que acabou de instalar não é a que está a correr.

Chamar as suas próprias ferramentas a partir de dentro de uma célula

Secção intitulada “Chamar as suas próprias ferramentas a partir de dentro de uma célula”
paths = tool("find", {"pattern": "**/*.dart", "path": "lib"})
for path in paths.splitlines()[:100]:
contents = tool("read", {"path": path})
...

tool(name, args) volta a entrar no registo de ferramentas do próprio agente. Isso significa que uma célula se pode distribuir por uma centena de ficheiros, ou delegar através de task, sem que o modelo gaste um turno por item.

Uma chamada através da ponte suspende o tempo limite da célula enquanto está pendente. O orçamento mede a inatividade, não o tempo real — uma célula que se distribui por subagentes e espera quatro minutos não está encravada, e matá-la a meio da distribuição perderia todo o estado do kernel.

eval(code: "…", reset: true, description: "Start a clean interpreter")

Descarta o interpretador e inicia um limpo. Tudo o que estava carregado desaparece, que é precisamente o objetivo.

No recinto da conversa, quando esta tem um; caso contrário, no anfitrião.

Um interpretador persistente controlado por um modelo que lê um repo não fidedigno é exatamente aquilo para que existe a execução apenas em recinto: uma chamada bash de execução única pelo menos termina, ao passo que um kernel é uma shell que se lembra.

Não arranca um recinto para lá chegar — a mesma regra que impede um separador de rig de arrancar automaticamente. Se quiser o kernel dentro de um recinto, abra primeiro a shell da conversa. Ver Dar a um agente uma máquina para testar.

  • Uma célula de cada vez por kernel. Duas células a competir num interpretador são duas metades de dois programas intercaladas num único espaço de nomes.
  • A saída tem um limite. Uma célula num ciclo de prints é truncada, em vez de lhe ser permitido encher a janela de contexto.
  • Quatro imagens por célula. Um ciclo de desenho pode emitir uma figura por iteração, e cada imagem tem um custo fixo elevado no pedido que a transporta.
  • O kernel morre com a execução. Um que ainda guarde um dataframe depois de a conversa terminar é uma fuga.