Un número son palabras

Qué mejor demostración de que un número son palabras que un traductor de números a palabras, así, tan absurdo como este que intenta transformar los números (dígitos) en palabras, especialmente orientado a crear un libro con las palabras de unos cuantos (indeterminados) decimales de números irracionales, pues hay pocas cosas más irracionales que este proyecto absurdo.

/********************************************************
    Proyecto tres14 (escrito en C)
    realizado por Giusseppe Domínguez
    a partir del día 8 de diciembre de 2019
********************************************************/

#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <time.h>
#include <ctype.h>
#define OK 1
#define KO 0
#define MAX_LONG 10 // Longitud máxima de nombre de dígito

int firma();
int digitea(char caracter);
int nombranumero(int idioma, char caracter, char *nombre);
int instrucciones(char *comando);

int main(int argc, char *argv[])
{
  int i, idioma=0;
  char nombrenumero[MAX_LONG], caracter;
  FILE *fp;
 
  if ((argc < 2) || (argc > 3)) { instrucciones(argv[0]); } // Faltan argumentos
  else if (argc == 2) { // Número desde línea de comando
    for (i=0; i<strlen(argv[1]); i++) {
      caracter=argv[1][i];
      if(! nombranumero(idioma, caracter, nombrenumero)) { instrucciones(argv[0]); return KO; }
      puts(nombrenumero);
    }
  }
  else if (argc == 3) { // Número en fichero argv[2]
    if ( (! isdigit(argv[1][0])) || ((idioma = digitea(argv[1][0])) > 1) ) {
      printf("[ERROR] No conocemos el idioma: %s\n", argv[1]);
      instrucciones(argv[0]);
    } 
    else if ((fp = fopen(argv[2],"r")) == NULL) {
      printf("[ERROR] intentando abrir el archivo %s\n", argv[2]);
      instrucciones(argv[0]);
    }
    else {
      while ((caracter = fgetc(fp)) != EOF) {
        if (caracter != '\n') { // Ignoramos los saltos de línea
          if (! nombranumero(idioma, caracter, nombrenumero)) { instrucciones(argv[0]); return KO; }
          printf("%s ", nombrenumero);
        }
      }
    }
  }
  printf("\n");
  firma();
  return OK;
}


/******************************************
  La función instrucciones hace lo que su nombre
  indica: Imprime las instrucciones del programa.
******************************************/
int instrucciones(char *comando) {
    printf("\nUtilización: %s [número_positivo] [idioma fichero]\n\n", comando);
    puts("Si introducimos un nombre de fichero, el primer parámetro indica el idioma");
    puts("Idioma puede ser:");
    puts("\t0 - Español");
    puts("\t1 - Inglés");
}

/******************************************
  La función nombranumero nombra el número
  contenido en el caracter (si procede, claro)
  y devuelve error si no lo consigue.
  idioma = 0 (español)
           1 (inglés)
******************************************/
int nombranumero(int idioma, char caracter, char *nombre) {
  int digito;
  static int nomascomas=0; // Para no encontrar más de una coma en un argumento
  // char *numeros[] = { "cero", "uno", "dos", "tres", "cuatro", "cinco", "seis", "siete", "ocho", "nueve" };
  char *numeros[2][MAX_LONG] = {
    { "cero", "uno", "dos", "tres", "cuatro", "cinco", "seis", "siete", "ocho", "nueve" },
    { "zero", "one", "two", "three", "for", "five", "six", "seven", "eigth", "nine" }
  };
  char *coma[] = { "coma", "point" };

  if ((caracter == ',') || (caracter == '.')) {
    strcpy(nombre, coma[idioma]);
    if (++nomascomas > 1) {
      printf("Un número no puede tener más de una coma\n");
      return KO;
    }
    return OK;
  }
  else if (isdigit(caracter)) {
    digito = digitea(caracter);
    strcpy(nombre, numeros[idioma][digito]);
    return OK;
  }
  printf("[ERROR] |%c| No es un caracter válido en un número positivo\n", caracter);
  strcpy(nombre, "ERROR");
  return KO;
}
/******************************************
  La función digitea devuelve un número entero
  a partir del caracter (char) proporcionado
******************************************/
int digitea(char caracter)
{
  int digito;
  digito = (int) (caracter + '0');
  digito -= 96;
  return digito;
}


int firma()
{
  time_t tiempo = time(0);
  struct tm *tiempolocal = localtime(&tiempo);
  char txt_firma[128];
  strftime(txt_firma,128,"\nGiusseppe Domínguez, a las %H:%M. M-%Y%m%d\n",tiempolocal);
  printf("%s\n",txt_firma);
  return OK;
}

qrqrqrqr de Carmen de la Rosa

Carmen de la Rosa

Entre los zapatos de cristal,
rosas de hielo
se me ha congelado el alma, cristalina
de azul fuego

Llegó anunciada de antaño y estaño vs. deambulando
por cúmulos de arena y brisa de seda
recia
crujiendo cobarde, de la rectitud al desplome y entre versos de longevas dinastías se alzó, como una sirena que atisba un barco desde su océano infinito.

Cuan si fuese poetisa, diosa del infinito
emergió

Y mientras la tinta,
negra,
de punta a punta
y gota a gota, se clavaba en edificios de mármol,
las palabras se deshacían.
La sal en el agua
y en la tierra sucumbieron.
La luz de la manta que me cobijaba se llenó de langostas
SÍ!
SÍ!
SÍ!

Y dándome cuenta las notas, la música, las campanas y el latido se hicieron una en el silencio.

Recibido desde su página personal el día 15 de enero de 2020, tras terminar la edición online del libro qrqrqrqr. Quizá aún dé tiempo de incluirla en la versión en papel.

qrqrqrqr

Libro de códigos QR y poemas escritos y enviados desde una dirección URL generada para la ocasión por 33 diferentes poetas.

En las ocasiones donde el o la poeta no hicieron llegar sus textos, se ha optado por dejar la referencia a la página web en cuestión por si alguien quiere tomar el relevo y enviar algún poema en su nombre de cara al futuro.

Como todo proyecto de arte postal, es una botella lanzada al océano que, en más ocasiones de las esperadas, regresa con provisiones para aguantar la vida.

Giusseppe Domínguez les propuso a 33 personas participar en este libro enviándoles por correo postal un código QR impreso sobre hojas de una edición de Las Flores del Mal, de Baudelaire, que redireccionaba a una página que contenía un formulario personalizado así como un código QR con el nombre de la persona invitada a formar parte del proyecto.

El libro contiene los QR personalizados para cada poeta, así como los poemas de aquellas personas que cumplimentaron sus formularios poéticos con un poema.

75% de despojos

de repente un día mueres

deja un 75% de despojos.

tres primeras sílabas
para decir lo obvio:
de la vida a la muerte
hay
un salto cuántico
un salto cualitativo
un salto irreversible

no puede ser de otro modo
tal como están definidas ambas palabras
en ese lenguaje
de lógica bivalente
tan binario
que garantiza principio del tercero excluso
tertium non datur

tres primeras sílabas
ejercitando oulipianamente
su apego a la única vocal
que Perec secuestra

tres segundas sílabas
que no lo parecen
por aquella sinalefa que ha sido ignorada
por aquel hiato que rompe el diptongo
por la preponderancia de vocales diferentes
que alcanza el 60%
de tan sólo (con tilde) cinco letras

tres segundas sílabas
que sitúan en el tiempo
absolutamente indefinido (en cuanto a cuándo
(¿qué día?)
absolutamente indefinido (en cuanto a cuánto
(¿día sidéreo o día solar?)

un suceso
que podemos calificar con once letras como
un suceso inacabable
un suceso inagotable
un suceso inapagable
un suceso inapelable
un suceso inatacable
un suceso inatajable
un suceso incachable
un suceso incalmable
un suceso incansable
un suceso incansable
un suceso incantable
un suceso incobrable
un suceso incontable
un suceso inculpable
un suceso indeseable
un suceso inevitable
un suceso inexorable
un suceso inexpiable
un suceso infaltable
un suceso inflamable
un suceso inglosable
un suceso ingustable
un suceso inhallable
un suceso inimitable
un suceso injertable
un suceso inllevable
un suceso inmancable
un suceso inoperable
un suceso inopinable
un suceso inoxidable
un suceso insaciable
un suceso insalvable
un suceso insociable
un suceso insoldable
un suceso insondable
un suceso intachable
un suceso integrable
un suceso intragable
un suceso intratable
un suceso intricable
un suceso inubicable
un suceso invadeable
un suceso invaluable
un suceso invariable
un suceso inviolable
un suceso inyectable

 
hasta que llegas al mismo
término
a esa segunda persona
que te asusta
porque asusta a otro
que somos yo

esas dos llanas sílabas
de las ocho iniciales
que son el despojo
que no son el despojo
que son la enjundia
el non plus ultra
el meollo de la frase
lo verdaderamente importante
y a lo que no quieres llegar
por lo que te amparas en otras seis
previas unidades silábicas
que te conducen
inexorablemente
al fin

Búsqueda de palabras en la RAE en línea de comandos

He fabricado un script (un lote de comandos) de bash shell en Linux para descargar y juguetear con búsquedas en la RAE, ya que resulta complicado pedir que tengan la deferencia de hacerla disponible para el público, como si la RAE fuese un organismo público pagado con dinero público.

Es el paso intermedio entre buscar una palabra y descargarme el diccionario completo palabra a palabra. Ahora toca hacer un pequeño programita que lo invoque para cada una de las palabras que tecleé para el proyecto de Isidoro Valcárcel Medina hace unos años y traiga sus definiciones.

Lo he llamado buscaenrae.sh.

Esta versión está modificada sobre la que publiqué hace unos días para subsanar errores relacionados con las palabras que contienen varias entradas/acepciones (no es lo mismo acepciones que entradas y soy consciente de ello, pero no es importante), así como para retirar las conjugaciones en los verbos.

#!/bin/bash

### FUNCIONES ÚTILES PARA EL PROGRAMA
# uso() Instrucciones del programa y salida en caso de error.
uso () {
  echo "Uso: $0 salida palabra"
  echo -e "\tsalida es un valor númerico que identifica:"
	echo -e "\t[0] para generar un archivo HTML con la respuesta"
	echo -e "\t[1] para generar un archivo TXT  con la respuesta"
	echo -e "\t[2] para generar una línea  TXT  con la respuesta"
  exit
}
f_verbos="00000_VERBOS.txt"
f_errores="00000_ERRORES.txt"

# CONTROL DE ENTRADA DE VARIABLES y ASIGNACIÓN
if [ $# -lt 2 ]
then
  # Reportar uso inapropiado
  uso
else
  salida=$1
  if [ $# -eq 2 ]; then
    palabra="$2"
  elif [ $# -eq 3 ]; then 
    palabra="$2 $3"
  elif [ $# -eq 4 ]; then 
    palabra="$2 $3 $4"
  elif [ $# -eq 5 ]; then 
    palabra="$2 $3 $4 $5"
  fi
  # echo "Palabra es #$palabra#"
fi

# CONSULTA DEL SERVIDOR de la RAE simulando ser uno de los diversos navegadores posibles
navegador=(
  "Mozilla/5.0 (X11; Ubuntu; Linux x86_64; rv:15.0) Gecko/20100101 Firefox/15.0.1"
  "Mozilla/5.0 (Windows NT 10.0; WOW64; rv:77.0) Gecko/20100101 Firefox/77.0"
  "Mozilla/5.0 (Windows NT 6.1; WOW64; rv:77.0) Gecko/20190101 Firefox/77.0"
  "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_9_3) AppleWebKit/537.75.14 (KHTML, like Gecko) Version/7.0.3 Safari/7046A194A"
)
rnd=`echo $(($RANDOM%${#navegador[@]}))` # Elegimos un navegador al azar
# Hacemos la petición a la web de la RAE
curl -s --user-agent "${navegador[$rnd]}" https://dle.rae.es/"$palabra" > ./"$palabra.html"

# PROCESAMOS EL ARCHIVO OBTENIDO (Cortamos, retiramos lo innecesario, etc)
# Si se trata de un verbo, quitar las conjugaciones
id_conjugacion="
" esunverbo=`grep -c "$id_conjugacion" ./"$palabra.html"` if [ $esunverbo -gt 0 ] then echo "$palabra es un verbo" >> $f_verbos # ELIMINAMOS la(s) CONJUGACIÓN(ES) sed -i "/${id_conjugacion}/d" ./"$palabra.html" fi # Si tiene más de una acepción (Calcular cuántas después de saber si es un verbo) id_acepcion="
" num_acepciones=`grep -c "$id_acepcion" ./"$palabra.html"` # Si no tiene acepciones, la palabra no existe. No continuamos. if [ $num_acepciones -eq 0 ] then echo "$palabra no se ha encontrado en la RAE" >> $f_errores rm "./$palabra.html" exit fi # PARTIR en $num_acepciones EL FICHERO $palabra.html" # acepciones y acepciones_fin son 2 arrays de líneas PRECISO CONVERTIRLOS a cortes[] acepciones=`grep -n "$id_acepcion" ./"$palabra.html"|awk -F":" '{print $1}'|sed ':a;N;$!ba;s/\n/ /g'` c=0 for i in $acepciones do let cortes[$c]=$(($i)) let c=$(($c+1)) done acepciones_fin=`grep -n "$id_acepcion_fin" ./"$palabra.html"|awk -F":" '{print $1}'|sed ':a;N;$!ba;s/\n/ /g'` c=0 for i in $acepciones_fin do let cortes_fin[$c]=$(($i)) let c=$(($c+1)) done # GENERA FICHEROS palabra.X.html por cada ACEPCIÓN for (( i=0; i<$num_acepciones; i++ )) do # echo "El comienzo del corte está en ${cortes[$((i))]}" # echo "El fin del corte está en ${cortes_fin[$((i))]}" sed "${cortes[$((i))]},${cortes_fin[$((i))]} !d" "./$palabra.html" > "./$palabra.$i.html" # Distintas salidas del programa, en función de la variable "salida" if [ $salida -gt 0 ] # Salida a modo TXT then w3m "./$palabra.$i.html" > "./$palabra.$i.txt" if [ $salida -gt 1 ] # En una sóla línea then sed ':a;N;$!ba;s/\n/ /g' "./$palabra.$i.txt"|sed 's/ / /g' > "./$palabra.$i.1linea" fi fi done # BORRAR indica si dejar o no los archivos que no se deseen como salida BORRAR=1 if [[ $BORRAR -eq 1 ]] && [[ $salida -gt 0 ]] then rm "./$palabra."*html if [ $salida -eq 2 ] then rm "./$palabra."*txt fi fi # SALIDA FORZADA exit

Las primeras pruebas las he realizado con la palabra palabra, como debe ser.

buscaenrae.sh 2 palabra

Potencias

Adoro las potencias del 3. Seguro que ya lo sabes si has leído algo de mi trabajo… sin ir más lejos el que está dedicado completamente a juegos con ello, como es el proyecto !ç~ñ¿.#.

Pero estaba jugueteando con darle una respuesta automática a un amigo sobre cuáles eran las potencias de 3 y no tenía ningún programita que las calculase. ¡¿Habrase visto?!

Así que tenía que hacerlo. Decidí hacerlo a partir de una modificación del 17 amores, que le regalé a Carmen en nuestro decimoséptimo aniversario. Aunque me precipité y lo escribí mal un par de veces (siendo algo trivial) por exceso de confianza. Aquí está la versión definitiva (muy muy mejorable), que me dan ganas de escribir también en Python o en BASIC.

#!/bin/bash
# Escribe todas las potencias de un número dado (3, por ejemplo)
# hasta una cantidad dada (17, por ejemplo)

razon=3;
producto=3;
cantidad=17;

for ((i=1; i<=$cantidad; i++)); do
  producto=$(($producto*$razon));
  echo -e $(($producto/$razon)) " x " $razon " = " $producto
done

Por supuesto, el resultado de esta ejecución es sencillo y casi diría tonto:

3 x 3 = 9
9 x 3 = 27
27 x 3 = 81
81 x 3 = 243
243 x 3 = 729
729 x 3 = 2187
2187 x 3 = 6561
6561 x 3 = 19683
19683 x 3 = 59049
59049 x 3 = 177147
177147 x 3 = 531441
531441 x 3 = 1594323
1594323 x 3 = 4782969
4782969 x 3 = 14348907
14348907 x 3 = 43046721
43046721 x 3 = 129140163
129140163 x 3 = 387420489

Un pequeño divertimento en Python

cuarentena=int(input("¿Cuántos días durará la cuarentena? "))
print("¿No tenéis la impresión de que un día se parece a otro día,", end="")
for i in range(cuarentena-1):
    print(" como en un bucle,", end="")
print(" como en un bucle?")

Un pequeño código que he hecho en python (casi podría decir que es mi primer o segundo programa en Python) a raíz de un texto que publicó un amigo en Facebook y que me dio la idea de meterlo en un bucle, como estaba pidiendo a gritos su pregunta.

Este es uno de los posibles resultados de la operación con un 999 que da bastante miedo.

Read moreUn pequeño divertimento en Python

primeros pasos con python

De manera muy tonta, ando hoy perdiendo el tiempo aprendiendo python, como si me hiciese alguna falta conocer un lenguaje más.

Todo ocurre por alguna razón (o no).

En esta ocasión «la culpa» la tiene una conversación con mi amiga Sofía sobre el lenguaje python. Yo le dije que se pusiese a aprenderlo por su cuenta, la verdad con la osadía que da la ignorancia, pues es un lenguaje de mucho más alto nivel de lo que yo imaginaba y es bastante complejo (y completo), aunque puede tener una curva de aprendizaje rápida y satisfactoria.

He encontrado este par de tutoriales para comenzar. Por lo menos a saber de qué se trata esto de la programación orientada a objetos con un lenguaje interpretado. Creo que de los que conozco es el único que agrupa estas dos propiedades.

Una sencilla introducción

Un completo tutorial (cuando se complica deriva a páginas en inglés)

720 maneras de escribir tu nombre

Gracias a la propuesta de «Amig@ invisible» a la que estuvimos jugando en el taller de Poesía y Escritura Creativa del grupo de los miércoles, me tocó hacerle un regalo a ISABEL y me planteé la curiosa propuesta de hacerle un pequeño obsequio sin adquirir absolutamente nada que no tuviese ya en mi poder.

Así que busqué un código que pudiese hacer permutaciones de palabras (sin repetición). Lo adapté a mis necesidades, aunque usar la palabra necesidad para esto no deja de tener algo de gracia, y generé un documento de las permutaciones que se pueden realizar con las 6 letras de la palabra ISABEL. A continuación, procedía hacer una desordenación aleatoria de las mismas con un comando linux bien sencillo:

sort -R isabel.txt > isabel_desordenada.txt

Lo más laborioso, pero también lo más bello, ha sido realizar la maquetación y posterior impresión de unos libretos con las 720 maneras de escribir su nombre, elegir la letra de la portada, en concreto, me ha llevado casi una mañana.

Las cartulinas que tenía disponibles para realizar la cubierta eran escasas y de un gramaje algo que pusieron en apuros (hasta casi estropear) a mi impresora Canon PIXMA 3650. Por supuesto, algunas de las tipografías elegidas para ser delicadas, como una Josefin Sans Light, apenas se ha impreso correctamente en varios de los ejemplares editados (no voy a realizar tiradas largas). Cada ejemplar de los así creados tendrán un precio de 6€ que era el máximo destinado al regalo del juego navideño.

Ahora me he encontrado con una fuente casi inagotable de generar publicaciones que me fascina: la utilización de la matemática y la informática para escribir textos poéticos delicados y dedicados, explorando la naturaleza corpórea del resultado en impresiones caseras sobre las que tengo un control exhaustivo y que me permiten, además, reutilizar materiales que casi tenía a punto de tirar (eso nunca, y lo sabes).

Esto no es una broma