sed, 299 + 1
Sí, sed puede encontrar una llama. No, sed no puede hacer matemáticas. Esta es la respuesta más larga hasta ahora, con 299 + 1 caracteres, porque tuve que enseñarle a contar.
Esta respuesta requiere un sed con expresiones regulares extendidas ( sed -Eo sed -r). Usé OpenBSD sed (1) . La entrada es una cadena por línea. (Por lo tanto, la cadena puede no contener una nueva línea). La salida es una línea de números, o nada.
Uso (+1 carácter para -r):
$ echo 'All arms on all shoulders may ache.' | sed -rf llama.sed
1 2 12 26 30
Código fuente (299 caracteres):
s/%/z/g
s/(.*)[Aa]/\1%/
s/(.*)[Mm](.*%)/\1%\2/
s/(.*)[Aa]((.*%){2})/\1%\2/
s/(.*)[Ll]((.*%){3})/\1%\2/
s/(.*)[Ll]((.*%){4})/\1%\2/
/(.*%){5}/!d
s/[^%]/z/g
:w
s/(z*)%/\10 z\1/
s/z*$//
s/z0/1/
s/z1/2/
s/z2/3/
s/z3/4/
s/z4/5/
s/z5/6/
s/z6/7/
s/z7/8/
s/z8/9/
s/([0-9]z*)z9/z\10/g
s/(z*)z9/1\10/
/[%z]/bw
El programa primero reemplaza la llama por cinco %. (Todos %en este programa son literales). El primer comando s/%/z/gcambia cualquiera %a zen la línea de entrada. Los siguientes cinco comandos encuentran la llama, por lo que todos los brazos en todos los hombros pueden doler. se convierte en A %% brazos en% ll hombros% ay% che. Como cada uno .*es codicioso, siempre encuentro la llama a la derecha: llama llama se convertiría en llama %%%%% . Si no puedo obtener cinco %, /(.*%){5}/!dborra la línea de entrada y omite los siguientes comandos.
s/[^%]/z/gcambia cada personaje excepto %a z. Entonces entro en un bucle. s/(z*)%/\10 z\1/cambia el primero %a 0, copia cero o más zde izquierda a derecha y agrega uno más za la derecha. Esto es para que el número de zsea igual al índice. Por ejemplo, se zz%zzz%...convierte en zz0 zzzzzzzz%...porque el primero %estaba en el índice 2, y el siguiente %en el índice 8. s/z*$//elimina más zdel final de la cadena.
Los siguientes once comandos cuentan zeliminando cada uno zy contando desde 0. Se cuenta como zzz0, zz1, z2, 3. Además, se 1zzzz9convierte z1zzz0(más tarde 23) o se zzzz9convierte 1zzz0(más tarde 13). Este ciclo continúa hasta que no haya más %o z.