Implementación · Tema 31

Reglas de derivación con JavaScript

Representá expresiones como datos, aplicá reglas simbólicas recursivas, simplificá resultados y verificá el derivador numéricamente.

01 · De fórmula a estructura

Un programa necesita comprender la expresión

Una cadena como "sin(x*x)" no revela directamente qué operación es exterior. Un derivador simbólico separa análisis, transformación, simplificación y presentación.

parse

Analizar

Convertir texto en un árbol de sintaxis.

derive

Transformar

Aplicar reglas según cada tipo de nodo.

simplify

Reducir

Eliminar ceros, unos y operaciones redundantes.

02 · Árbol de sintaxis

Las expresiones como objetos

El polinomio x²+3x puede representarse sin ambigüedad:

const expression = {
  type: "add",
  left: { type: "power", base: { type: "variable", name: "x" }, exponent: 2 },
  right: {
    type: "multiply",
    left: { type: "constant", value: 3 },
    right: { type: "variable", name: "x" }
  }
};

Cada nodo contiene solo los operandos necesarios. El árbol conserva precedencia y facilita recorridos recursivos.

03 · Reglas mínimas

Constantes y variables detienen la recursión

D[c]=0    D[x]=1    D[y]=0, si derivamos respecto de x
function derive(node, variable = "x") {
  switch (node.type) {
    case "constant": return constant(0);
    case "variable": return constant(node.name === variable ? 1 : 0);
    default: throw new Error(`Nodo no soportado: ${node.type}`);
  }
}

04 · Sumas y restas

Conservar el operador y derivar los hijos

case "add":
  return add(derive(node.left, variable), derive(node.right, variable));
case "subtract":
  return subtract(derive(node.left, variable), derive(node.right, variable));

La recursión refleja exactamente la linealidad: el derivador no necesita saber cuántos términos contiene la expresión completa.

05 · Operaciones binarias

Producto y cociente construyen nuevos árboles

case "multiply":
  return add(
    multiply(derive(node.left, variable), node.right),
    multiply(node.left, derive(node.right, variable))
  );
case "divide":
  return divide(
    subtract(
      multiply(derive(node.top, variable), node.bottom),
      multiply(node.top, derive(node.bottom, variable))
    ),
    power(node.bottom, 2)
  );

En una implementación inmutable conviene clonar o tratar los nodos como valores para evitar modificaciones accidentales compartidas.

06 · Potencias

Distinguir exponente constante y variable

Para uⁿ con n constante:

case "power": {
  const { base, exponent } = node;
  if (typeof exponent === "number") {
    return multiply(
      multiply(constant(exponent), power(base, exponent - 1)),
      derive(base, variable)
    );
  }
  return deriveVariablePower(base, exponent, variable);
}

La potencia variable necesita la regla logarítmica del tema 27.

07 · Regla de la cadena

Funciones elementales como nodos unarios

Transformaciones simbólicas.
NodoDerivada exteriorResultado completo
sin(u)cos(u)cos(u)u′
cos(u)−sin(u)−sin(u)u′
exp(u)exp(u)exp(u)u′
log(u)1/uu′/u

Todos los casos derivan recursivamente el argumento, lo que implementa la cadena.

08 · Simplificación

Una derivada correcta puede ser ilegible

Derivar 3x produce inicialmente 0·x+3·1. Reglas locales mejoran el resultado:

0+u→u   1·u→u   0·u→0   u⁰→1   u¹→u
function simplifyMultiply(left, right) {
  if (isZero(left) || isZero(right)) return constant(0);
  if (isOne(left)) return right;
  if (isOne(right)) return left;
  if (isConstant(left) && isConstant(right)) {
    return constant(left.value * right.value);
  }
  return multiply(left, right);
}

09 · Evaluación segura

Recorrer el árbol sin eval

function evaluate(node, scope) {
  switch (node.type) {
    case "constant": return node.value;
    case "variable": return scope[node.name];
    case "add": return evaluate(node.left, scope) + evaluate(node.right, scope);
    case "multiply": return evaluate(node.left, scope) * evaluate(node.right, scope);
    case "sin": return Math.sin(evaluate(node.argument, scope));
    default: throw new Error(`No se puede evaluar ${node.type}`);
  }
}

eval mezcla datos con código, dificulta validar entradas y abre riesgos de seguridad. Un intérprete explícito admite solo las operaciones declaradas.

10 · Flujo completo

Separar responsabilidades

textotokensASTderivarsimplificarimprimir

El lexer reconoce números y símbolos; el parser aplica gramática y precedencia; el derivador transforma el AST; el simplificador normaliza; el impresor genera una representación legible. Esta separación hace que cada etapa pueda probarse de manera independiente.

11 · Exploración interactiva

Laboratorio: derivada simbólica y numérica

Seleccioná una expresión, mové el punto y reducí h. La curva amarilla es la función y la coral su derivada.

EXPERIMENTO 31

Verificar reglas implementadas

f(x)=x³−2x

Los resultados aparecen debajo.
Derivada simbólica3x²−2
Valor simbólico1
Diferencia central≈ 1
Error absoluto≈ 0,000001

La comprobación numérica coincide con la regla simbólica.

12 · Estrategia de pruebas

Probar estructura y significado

Un derivador requiere varios niveles:

  • Pruebas unitarias para cada regla.
  • Pruebas estructurales del AST resultante.
  • Evaluaciones en puntos conocidos.
  • Comparación con diferencias centrales.
  • Casos de dominio inválido y errores esperados.

La verificación numérica detecta muchos fallos, pero no demuestra equivalencia simbólica en todo el dominio.

13 · Alcance del prototipo

Qué falta para un sistema algebraico completo

Un derivador real debe manejar análisis sintáctico, supuestos de dominio, simplificación canónica, expresiones equivalentes, funciones por partes, números complejos y crecimiento del árbol. También debe impedir recursión excesiva y validar tamaños de entrada.

La diferenciación automática usada en aprendizaje automático es distinta: calcula derivadas de un programa evaluado, no necesariamente una fórmula simbólica legible.

14 · Comprensión

Confusiones frecuentes

«Basta reemplazar texto para derivar»

Las sustituciones ignoran precedencia, anidamiento y estructura.

«eval es la forma más sencilla y segura»

Ejecuta código arbitrario; es preferible interpretar un AST validado.

«Simplificar y derivar son la misma etapa»

Conviene separarlas para probar corrección y controlar transformaciones.

«Una coincidencia numérica demuestra equivalencia»

Solo aporta evidencia en los puntos probados.

«Todas las fórmulas son válidas en cualquier dominio»

El AST debe conservar restricciones de logaritmos, raíces y denominadores.

15 · Práctica guiada

Ejercicios de aplicación

Ejercicio 1: nodo constante

Implementá la derivada de una constante.

Ver solución

Debe devolver siempre {type:"constant", value:0}.

Ejercicio 2: regla de suma

Construí el AST derivado de x²+sin x.

Ver solución razonada

Se obtiene una suma cuyos hijos representan 2x y cos x.

Ejercicio 3: producto

Derivá simbólicamente x·eˣ.

Ver solución

La regla genera 1·eˣ+x·eˣ, que se simplifica a eˣ(1+x).

Ejercicio 4: cadena

Indicá los nodos de la derivada de sin(x²).

Ver solución razonada

Un producto entre cos(x²) y la derivada de , simplificada a 2x.

Ejercicio 5: simplificación

Simplificá 0·x+3·1.

Ver solución

0·x→0, 3·1→3 y 0+3→3.

Ejercicio 6: evaluación

Evaluá el AST de x²+1 con x=3.

Ver solución

El resultado es 3²+1=10.

Ejercicio 7: prueba numérica

¿Cómo comprobarías la derivada implementada de ln(x)?

Ver solución razonada

Compararía 1/x con una diferencia central en varios puntos positivos y con distintos pasos.

Ejercicio 8: seguridad

¿Por qué un conjunto cerrado de nodos es preferible a eval?

Ver solución razonada

Solo permite operaciones conocidas, facilita validar datos y evita ejecutar código arbitrario.

16 · Síntesis

Ideas para recordar

  • Una expresión simbólica se representa mejor como árbol que como texto.
  • Derivar es una transformación recursiva guiada por el tipo de nodo.
  • La regla de la cadena aparece al derivar argumentos hijos.
  • Simplificación, evaluación e impresión son etapas independientes.
  • Un intérprete de AST es más controlable que eval.
  • Las diferencias centrales ayudan a verificar, pero no demuestran equivalencia global.

Con este tema se integran las reglas matemáticas del curso en una arquitectura de software extensible.