Efectos algebraicos
Lo que una función hace queda escrito en su tipo, y tú decides cómo se resuelve con un manejador. Adiós al async/await que contagia toda la cadena de llamadas.
fn greet(name: String) : Unit / Log {
Log.log("hello, #{name}")
} Lenguaje funcional con efectos algebraicos y fibras aisladas. Sin recolector de basura ni verificador de préstamos.
curl -fsSL https://raw.githubusercontent.com/kaikailang-org/kaikai/main/install.sh | sh effect Log {
log(msg: String) : Unit
}
fn greet(name: String) : Unit / Log {
Log.log("hello, #{name}")
}
fn main() {
handle {
greet("kaikai")
greet("world")
} with Log {
log(msg, resume) -> {
println("[INFO] #{msg}")
resume(())
}
}
}$ kai run effect.kai[INFO] hello, kaikai
[INFO] hello, world Agentes primero
Un lenguaje nuevo no tiene millones de programas de los que un modelo pueda aprender. kaikai apuesta por otro camino: el compilador responde con datos precisos, y el agente itera hasta llegar al programa correcto.
1Tú escribes la firma
fn aprobados(notas: [(String, Int)]) : [String] = ?cuerpo 2El compilador responde
$ kai build --holes-json{
"name": "cuerpo",
"expected_type": "[String]",
"in_scope": [
{"name": "notas", "type": "[(String, Int)]"}
],
"candidates": [
{"expr": "[]", "kind": "literal"}
]
} 3El agente completa
fn aprobados(notas: [(String, Int)]) : [String] =
notas
|? . .1 >= 4
| . .0
|> list.sort kai build --holes-json Qué tipo espera cada hueco, qué hay en alcance y qué candidatos calzan. kai build --diags-json Los errores con archivo, línea y mensaje, listos para procesar. kai build --effects-json Los efectos de cada función. Saber si toca el disco no requiere leer el código. kai check --json El resultado de cada prueba y el contraejemplo exacto cuando una propiedad falla. kai info llm La guía de arranque para un agente que llega a un repositorio kaikai. kai info <tema> --json La documentación del lenguaje como datos, sin abrir un navegador. Este sitio también se presenta a los modelos en llms.txt, y el capítulo 15 del libro cuenta el flujo completo.
Seis ideas que definen el lenguaje, cada una con el código que la muestra.
Lo que una función hace queda escrito en su tipo, y tú decides cómo se resuelve con un manejador. Adiós al async/await que contagia toda la cadena de llamadas.
fn greet(name: String) : Unit / Log {
Log.log("hello, #{name}")
} Cuatro operadores, cuatro intenciones: |> aplica, | transforma, || aplana y |? filtra. Sabes qué hace cada paso antes de leer la función.
let total = [1..4]
| cuadrado
|| divisores
|? es_par
|> list.sum Conteo de referencias Perceus y fibras aisladas. Cada fibra cuida su propia memoria, así que no hay pausas globales ni un verificador de préstamos al que convencer.
let f = spawn.spawn { trabajador("B", 3) }
trabajador("A", 3)
spawn.await(f) Real<m/s> para medidas, monedas que no se mezclan y regiones de memoria con region { }. La información va en el tipo y no cuesta nada al ejecutar.
fn convertir_a_usd(monto: Real<EUR>, tasa: Real<USD/EUR>) : Real<USD>
= monto * tasa requires, ensures e Int where >= 0. Lo que la función exige y lo que promete se escribe junto a ella, al estilo de SPARK y sin un demostrador SMT.
fn dividir(a: Int, b: Int) : Int
requires b != 0
ensures result * b == a
{
a / b
} Deja un hueco con ? y el compilador te cuenta qué tipo espera ahí, también en JSON. Pensado para que personas y agentes escriban juntos.
fn area_circulo(r: Real) : Real = ?formula $ kai build --holes-json"expected_type": "Real" Un programa completo con su salida. Toma los números del 1 al 4 y encadena las cuatro tuberías para sumar los cuadrados pares.
Ver los doce ejemplosfn cuadrado(n: Int) : Int = n * n
fn divisores(n: Int) : [Int] = [1, n]
fn es_par(n: Int) : Bool = n % 2 == 0
fn main() {
# `[1..4]` es un literal de rango: no hace falta un acumulador a mano.
# `[1..10..2]` agrega un paso.
let total = [1..4] # [1, 2, 3, 4]
| cuadrado # [1, 4, 9, 16] (transforma)
|| divisores # [1, 1, 1, 4, 1, 9, 1, 16] (aplana)
|? es_par # [4, 16] (filtra)
|> list.sum # 20 (aplica)
println("total=#{total}")
}$ kai run 06_pipes.kaitotal=20 Se instala con un solo comando en macOS, Linux y Windows (con WSL2), sin dependencias. Y el libro te acompaña desde el primer programa hasta un caso de estudio completo.
curl -fsSL https://raw.githubusercontent.com/kaikailang-org/kaikai/main/install.sh | sh