¿Te resulta más fácil leer con fondo crema, un tono de color, más contraste o un texto más grande? Elige tus colores y tu texto una sola vez, para todas las páginas.

Lección gratuita

Cómo funcionan los adaptadores LoRA

Después de esta lección: Puedo explicar por qué un adaptador pequeño cambia barato un modelo grande.

Lección de 60 min6 comandosLaboratorio de agente de programación con IA: usa opencode para explicar y corregir código, y comprueba su trabajo

Cambia un poco y deja el resto

Un modelo grande tiene miles de millones de números. Entrenarlos todos exige mucha memoria y mucho tiempo. Un adaptador, como un LoRA, entrena unos pocos números extra junto a los grandes y no toca los grandes.

Esta lección cuenta esos números. Ningún laboratorio entrena un modelo, así que el trabajo es aritmética que ejecutas tú.

Al final de esta lección

Nota

Puedo explicar por qué un adaptador pequeño cambia barato un modelo grande.

Palabras clave

PalabraQué significa
Parámetroun número que el modelo ha aprendido
Congeladoque no cambia durante el entrenamiento
Adaptadorun pequeño conjunto de números nuevos entrenados
Rangolo delgadas que son las dos tablas del adaptador
LoRAun adaptador hecho de dos tablas delgadas

Las celdas que rellenan los estudiantes quedan en blanco en esta vista previa.

Una capa es una tabla de números

Dentro de un modelo, una capa es sobre todo una tabla de números. Una tabla de 6 filas y 6 columnas guarda 6 por 6, es decir, 36 parámetros. Una tabla de 100 por 100 guarda 10 000.

El entrenamiento completo cambia todos los números de todas las tablas. Por eso es caro.

Dos tablas delgadas hacen un cambio completo

Multiplica una tabla de 6 por 1 por otra de 1 por 6 y obtienes una tabla de 6 por 6. Tiene la forma de la tabla congelada, así que se puede sumar a ella.

El adaptador guarda 6 más 6, es decir, 12 números, en lugar de 36. El rango es el lado delgado. Un rango mayor guarda más y cuesta más.

Ejemplo resuelto: una tabla de 100 por 100

RangoNúmeros del adaptadorParte de los 10 000
11 x (100 + 100) = 2002 %
44 x 200 = 8008 %
88 x 200 = 160016 %

Las celdas que rellenan los estudiantes quedan en blanco en esta vista previa.

Un error frecuente

Advertencia

Mucha gente cree que un adaptador es una copia más pequeña del modelo. No lo es. El modelo grande se queda como está y el adaptador se suma a su salida. Quita el adaptador y recuperas el modelo original.

Escribe el ayudante del modelo, parte 1

Comando
docker exec -w /home/node/project agent sh -c "printf '%s\n' 'const base = process.env.AI_URL || \"http://ai:4000\";' '// Los tokens de una respuesta, o null si no trae ninguno.' 'function count(data, name) {' '  return data.usage && typeof data.usage[name] === \"number\" ? data.usage[name] : null;' '}' > model.js"

Se muestra aquí y no se ejecuta. Crea una cuenta gratuita para pulsar Ejecutar y escribirlo en el terminal de tu propio laboratorio.

Escribe el ayudante del modelo, parte 2

Comando
docker exec -w /home/node/project agent sh -c "printf '%s\n' 'async function ask(messages, sample, max) {' '  try {' '    const res = await fetch(base + \"/v1/chat/completions\", {' '      method: \"POST\",' '      headers: { \"content-type\": \"application/json\", authorization: \"Bearer lab\" },' '      body: JSON.stringify({ model: \"lab\", messages: messages, max_tokens: max || 100 }),' '      signal: AbortSignal.timeout(30000),' '    });' '    if (res.ok === false) throw new Error(\"estado \" + res.status);' '    const d = await res.json();' '    return { text: d.choices[0].message.content, inTokens: count(d, \"prompt_tokens\"), outTokens: count(d, \"completion_tokens\"), recorded: false };' '  } catch (error) {' '    console.log(\"Muestra grabada: ningún modelo respondió (\" + error.message + \").\");' '    return { text: sample, inTokens: null, outTokens: null, recorded: true };' '  }' '}' 'module.exports = { ask };' >> model.js"

Se muestra aquí y no se ejecuta. Crea una cuenta gratuita para pulsar Ejecutar y escribirlo en el terminal de tu propio laboratorio.

Escribe el contador del adaptador, parte 1

Comando
docker exec -w /home/node/project agent sh -c "printf '%s\n' 'const { ask } = require(\"./model\");' '// Una tabla W congelada de 6 por 6 y dos delgadas: B es de 6 por 1 y A es de 1 por 6.' 'const rows = 6, cols = 6, rank = 1;' 'const B = [1, 2, 0, 1, 0, 3];' 'const A = [2, 0, 1, 0, 1, 1];' > adapt4.js"

Se muestra aquí y no se ejecuta. Crea una cuenta gratuita para pulsar Ejecutar y escribirlo en el terminal de tu propio laboratorio.

Escribe el contador del adaptador, parte 2

Comando
docker exec -w /home/node/project agent sh -c "printf '%s\n' 'function delta(i, j) {' '  let sum = 0;' '  for (let k = 0; k < rank; k++) sum = sum + B[i * rank + k] * A[k * cols + j];' '  return sum;' '}' 'const full = rows * cols;' 'const adapter = rank * (rows + cols);' >> adapt4.js"

Se muestra aquí y no se ejecuta. Crea una cuenta gratuita para pulsar Ejecutar y escribirlo en el terminal de tu propio laboratorio.

Escribe el contador del adaptador, parte 3

Comando
docker exec -w /home/node/project agent sh -c "printf '%s\n' 'async function main() {' '  console.log(\"tabla congelada: \" + rows + \" x \" + cols + \" = \" + full + \" números\");' '  console.log(\"adaptador: \" + rows + \" x \" + rank + \" más \" + rank + \" x \" + cols + \" = \" + adapter + \" números\");' '  const first = [];' '  for (let j = 0; j < cols; j++) first.push(delta(0, j));' '  console.log(\"cambio en la fila 0: \" + first.join(\" \"));' '  console.log(\"parte entrenada: \" + Math.floor((adapter * 100) / full) + \" %\");' '  const q = \"En una frase, ¿por qué entrenar un adaptador pequeño es más barato que entrenar todo el modelo?\";' '  const sample = \"Solo cambian las tablas pequeñas del adaptador, así que se guardan y se actualizan muchos menos números.\";' '  const reply = await ask([{ role: \"user\", content: q }], sample, 40);' '  console.log(\"el modelo dijo: \" + reply.text);' '}' 'main();' >> adapt4.js"

Se muestra aquí y no se ejecuta. Crea una cuenta gratuita para pulsar Ejecutar y escribirlo en el terminal de tu propio laboratorio.

Ejecuta el contador del adaptador

Comando
docker exec -w /home/node/project agent node adapt4.js

Se muestra aquí y no se ejecuta. Crea una cuenta gratuita para pulsar Ejecutar y escribirlo en el terminal de tu propio laboratorio.

Lo que imprimió el contador

Imprime el tamaño de la tabla congelada, el del adaptador, una fila del cambio y la parte entrenada. Los números de A y B son inventados. Un adaptador real los aprende.

La última línea es una llamada corta al modelo, o una Muestra grabada.

Sobre este laboratorio y su código: Laboratorio de agente de programación con IA: usa opencode para explicar y corregir código, y comprueba su trabajo

¿Enseñas a una clase? Asigna este módulo a tus alumnos con guía del profesor, tareas con corrección automática y un laboratorio para cada alumno.