jueves, 21 de junio de 2018

Probando Chessuino


Cheesduino, es una gran iniciativa puesto que te ofrece ...

Estas son algunas partidas en las que he tenido más suerte.

1. e4 Nc6 2. Bc4 Ne5 3. Bb3 c5 4. c3 Nd3+ 5. Kf1 Nf6 6. Bc4 Nxc1 7. Qxc1 Nxe4 8. Qc2 d5 9. Be2 Bf5 10. d4 Nxf2 11. Qxf5 Nxh1 12. Bh5 g6 13. Qg5 gxh5 14. Nf3 Qb6 15. Nbd2 Qxb2 16. Re1 Rd8 17. Qxh5 Qxc3 18. Ne5 Qxd2 19. Qxf7#

1. e4 g6 2. Nc3 Nc6 3. Nf3 f5 4. Bc4 Nf6 5. Ng5 a5 6. Bf7#
1. e4 g6 2. Nc3 c5 3. Nf3 Nc6 4. Bc4 f5 5. Ng5 Nf6 6. Bf7#

miércoles, 20 de junio de 2018

Probando Onyx de Novag a nivel 1.


Onyx de Novag (va con un pequeño tablero magnético). Testeada a su nivel más básico.


1. e4 e5 2. Nf3 Nf6 3. Bb5 Bd6 4. Qe2 O-O 5. O-O Qe8 6. d4 exd4 7. Bd3 Nc6 8. Bg5 Nxe4 9. Nh4 Nxg5 10. Qh5 Qe5 11. f4 Qe3+ 12. Kh1 Bxf4 13. Nf3 Nxf3 14. Qxh7#

Otro ejemplo.

1. e4 Nf6 2. Nc3 e5 3. Nf3 Nc6 4. Bb5 Bd6 5. O-O O-O 6. d3 Nb4 7. d4 exd4 8. Qxd4 Nxc2 9. Qd3 Nxa1 10. Ng5 Be5 11. Qh3 d6 12. Qh4 Bg4 13. Nd5 Nc2 14. Nxf6+ Qxf6 15. Qxh7#

martes, 19 de junio de 2018

Palma de mano en Jiusion USB microscope a 40x

La cámara ofrece una resolución de 640x480px que para móvil, Internet e inspección es suficiente. La calidad óptica de imagen es buena. Evidentemente, existen trastos de alta resolución y lentes de cristal pero aquí nos interesa la relación calidad precio.

Esta es la palma de mi mano

Y esta es la misma a 40x con el microscopio/lupa USB. Donde pueden apreciarse los poros.

Es recomendable en este tipo de imágenes realizar algo de "postproducción", he resaltado los detalles, así a lo guarro, con el software Fotoxx de Linux, que te lo hace con unos cuantos "clicks" sin que te tengas que comer mucho el coco.

Haciendo esto:
  • #Histograma 
    • Recorte de extremos 
  • #Efectos
    • Enfocar 
  • #Retocar luz y color
    •  menos contraste
    •  más color
Se llega a esto que resalta más los detalles.

La cámara promete unos falsos 1000x, que deben ser unos 200x reales o así. De todas formas la mejor franja de trabajo para estos aparatos es en el rango mínimo. Una gran ventaja de esta cámara es la de conectarla a móviles y tabletas que tengan función OTG. Si el móvil no dispone de ella, de todas formas siempre puede usarse como una webcam.

martes, 12 de junio de 2018

Chess Challenger Level 1, otra partida.

%Created by Caissa's Web PGN Editor 1. e4 e5 2. Nf3 Nc6 3. Bc4 Bc5 4. O-O Nf6 5. Re1 d6 6. Ng5 Bg4 7. Be2 Bxe2 8. Qxe2 Nd4 9. Qc4 b6 10. Qxf7#

viernes, 8 de junio de 2018

Partida chess challenger. Rápida.

Partida reiniciada contra Chess Challenger a nivel 1.
1. e4 e5 2. f4 exf4 3. Nf3 d5 4. Nc3 dxe4 5. Nxe4 Bf5 6. Qe2 Qd5 7. Nf6+ Kd8 8. Qe8#

miércoles, 6 de junio de 2018

Partida Chess Challenger 10.

A nivel 1. :-)
1. e4 e5 2. Nf3 Nc6 3. Bc4 Bc5 4. O-O Nf6 5. Ng5 d5 6. exd5 Nxd5 7. Nc3 Qxg5 8. Nxd5 Kd8 9. d3 Qh4 10. Qf3 Be6 11. g3 Qg4 12. Kg2 Nd4 13. Qe4 Qh5 14. c3 Nc2 15. d4 Nxd4 16. cxd4 exd4 17. Nf4 Qg6 18. Nxg6 hxg6 19. Bg5+ Kc8 20. Bxe6+ fxe6 21. Qxe6+ Kb8 22. Rfe1 d3 23. Qe8+ Rxe8 24. Rxe8#

martes, 5 de junio de 2018

Chess Challenger 1978!

From a second hand marked.

Problemas de microtomía

Problema
La sección de parafina se curva o enrolla.

Causas
  • La cuchilla ha perdido el filo.
  • El angulo de corte es demasiado grande.

Fuente.
https://es.slideshare.net/vikashkr756/short-talk-final

lunes, 4 de junio de 2018

Foldable Slide Ringing Table DIY

See:

http://www.microscopy-uk.org.uk/mag/indexmag.html?http://www.microscopy-uk.org.uk/mag/artjan01/rmtable.html

Pruebas con espectroscopio casero

El la web encontrareis centenares de páginas sobre como construir un espectroscopio con un CD (o DVD). Yo hice el mio y aquí aparecen algunos resultados. Evidentemente, todo es muy rudimentario, pero resulta interesante. 

Espectro de una lampara incandescente.

Espectro discreto de una lampara de bajo consumo

En el del fluorescente se observan las bandas del mercurio. 

  
Espectro del Sol y de un LED RGB. (Red, Green, Blue)

viernes, 18 de mayo de 2018

Arduino DIY centrifuge

Now I am working on a DIY mini centrifuge.

For this project I use a hard disk motor. This motor is brushless, so it produces little friction and can reach higher speeds than standard motors. Furthermore, it is very easy to recycle one from an old hard disk.

I make the centrifuge enclosure with layers of Wood. I carved out different shapes to make space for the electronic components inside, as shown in the picture.




The centrifuge will be controlled by an Arduino micro controller. I will use an infrared sensor to count how fast the motor spins.

I have an old lab centrifuge which I bought in a second hand market. I put a tachometer, based also on an arduino, into that apparatus. Then, I realized that the centrifuge speed tended to change progressively. Its speed was unstable.

In this mini centrifuge, the arduino will hopefully regulate the engine speed if that differs from the speed set by the arduino. I use a special electronic component: "Electronic Speed Control", or ESC, which is used to control brushless drone or helicopter motors, too. That device allows the arduino to control the motor easily.

Using a little screen and three buttons, it will be possible to program the speed and time of working of the centrifuge.



People in Italki had helped me whit this text


Finally...

Arduino code, for not lose it.

/*
Centrifuga.
T. Espinosa. 2018.
*/

//######################################################
//# LIBRERIAS ##########################################
//######################################################
#include  <Wire.h>
#include  <LiquidCrystal_I2C.h>
#include <Servo.h>

//######################################################
//# VARIABLES Y ETC ####################################
//######################################################

//GND de fuente y Arduino siempre conectados. OJO!

//------------------------------------------------------
//- MOTOR   --------------------------------------------
//------------------------------------------------------
Servo servo;
Servo servoBrazo;
int servoPos = 0;

//------------------------------------------------------
//- variables   --------------------------------------------
//------------------------------------------------------

 unsigned long tiempo = 60;//Tiempo base

//------------------------------------------------------
//- TACOMETRO  --------------------------------------------
//------------------------------------------------------
float rev=0;

int rpm2;
int oldtime=0;
int timex;

void isr(){//funcion que llama la inerrupcion
rev++;//incrementa revoluciones en 1
}

/*
 Valores verificados empiricamente:
 servo 85. 14vps -- 840rpm
 servo 95. 30vps -1800rpm
 servo 105. 44 vps--2640 rpm
 servo 110. 60 vps-- 3600rpm. 

 Las interrupciones cuentan de más, supongo que por el tipo de lectura, prefiero ajustar empiricamente y ya está.
  */

//------------------------------------------------------
//- LCD ------------------------------------------------
//------------------------------------------------------

// Aqui se configuran los pines asignados a la pantalla del PCF8574
LiquidCrystal_I2C lcd(0x27, 2, 1, 0, 4, 5, 6, 7, 3, POSITIVE);
//Pines: SCL ->A0, SDA ->A1. Son estandart.


//------------------------------------------------------
//- BOTONES --------------------------------------------
//------------------------------------------------------

const int bot_blue = 6;//BOTON AZUL
const int bot_up = 3;
const int bot_down = 4;

//------------------------------------------------------
//- BUZZER --------------------------------------------
//------------------------------------------------------

const int buzzer = 5;
void s_entrada()
{
  for(int i =0 ;i<2;i++)
  {
  tone(buzzer, 3800, 80);//frecuencia, milisegundos
  delay(120);
  tone(buzzer, 3800, 80);//frecuencia, milisegundos
  delay(120);
  }
}
//-----------------------
void sonido_fin()
{
   int trono=300;
  
      for (int x=0;x<12; x++)
      {
         tone(buzzer, trono, 100);     
         delay(130);
         trono=trono+200;
       }
}


//######################################################
//# SETUP  #############################################
//######################################################

void setup()
{
   Serial.begin(9600);
  attachInterrupt(0,isr,RISING); //para poner en setup ¿?¿? 0 es pin 2, 1 es pin 3.
 servoBrazo.write(0);//emieza con motor apagado

  lcd.begin(16, 2);// Indica  LCD 16x2

  pinMode(bot_blue, INPUT);  //BOTONES
  pinMode(bot_up, INPUT); 
  pinMode(bot_down  , INPUT); 
 servoBrazo.attach(9);//donde va el motor

  for(int i = 0; i< 3; i++)//3 PARPADEOS DE LUZ DE PANTALLA
  {
    lcd.backlight();
    delay(150);
    lcd.noBacklight();
    delay(150);
     tone(buzzer, 4800, 80);//frecuencia, milisegundos
  }
   lcd.backlight();
  delay(400);
  // Mover el cursor a la primera posición de la pantalla (0, 0)
  lcd.setCursor ( 0, 0 );
  lcd.print("---CENTRIFUGA---");
  // Mover el cursor a la segunda linea (1) primera columna
  lcd.setCursor ( 0, 1 );
  // Imprimir otra cadena en esta posicion
  lcd.print("Pulsa Boton Azul");

}

//######################################################
//# INICIO  #############################################
//######################################################

void loop()
{

  int boton_azul = digitalRead(bot_blue);

  while(boton_azul == LOW) //espera que se apriete azul
    {   
      boton_azul = digitalRead(bot_blue);
      delay(100);
     }
    
   tone(buzzer, 3000, 100);//frecuencia, milisegundos
   delay(500);
   lcd.clear();//limpia pantalla
  
 boton_azul = digitalRead(bot_blue);  //lectura digital de
 int boton_up = digitalRead(bot_up);
 int boton_down = digitalRead(bot_down);

 int revol = 2000;

 s_entrada();//sonido al entrar
while(boton_azul == LOW) //PREGUNTA RPM ------------------------------------------
    {
     lcd.setCursor ( 0, 0 );
     lcd.print("RPM:     Ajuste");
     lcd.setCursor ( 4, 0 );
     lcd.print("    ");
     lcd.setCursor ( 4, 0 );
     lcd.print(revol);
     lcd.setCursor ( 0, 1 );        
     lcd.print("Salir Pulsa Azul");

     int boton_up = digitalRead(bot_up);
     int boton_down = digitalRead(bot_down);

     if (boton_up == HIGH)
          {
          tone(buzzer, 2000, 100);//frecuencia, milisegundos
          delay(80);
          revol=revol+25;
          if (revol > 9500){revol = 9500;}
          boton_up = digitalRead(bot_up);
          }
     if (boton_down == HIGH)
          {
          tone(buzzer, 2000, 100);//frecuencia, milisegundos
          delay(80);
          revol=revol-25;
         if (revol < 0){revol = 0;}
          boton_down = digitalRead(bot_down);
            }
               
     delay(50);
    
    boton_azul = digitalRead(bot_blue); 
    }
       lcd.clear();//limpia pantalla
        boton_azul = LOW; 

  tiempo=60;

   s_entrada();//sonido al entrar
   delay(500);
  
    while(boton_azul == LOW) //PREGUNTA TIEMPO------------------------
    {
     lcd.setCursor ( 0, 0 );
     lcd.print("Time:    Ajuste");
     lcd.setCursor ( 5, 0 );
     lcd.print("    ");
     lcd.setCursor ( 5, 0 );
     lcd.print(tiempo);
     lcd.setCursor ( 0, 1 );        
     lcd.print("Salir Pulsa Azul");

     int boton_up = digitalRead(bot_up);
     int boton_down = digitalRead(bot_down);

     if (boton_up == HIGH)
          {
          tone(buzzer, 2000, 100);//frecuencia, milisegundos
          delay(100);
         tiempo=tiempo+10;
          boton_up = digitalRead(bot_up);
          }
     if (boton_down == HIGH)
          {
          tone(buzzer, 2000, 100);//frecuencia, milisegundos
          delay(100);
           tiempo=tiempo-10;
        if (tiempo > 100000){tiempo = 0;}
          boton_down = digitalRead(bot_down);
            }
       
     delay(80);
    
    boton_azul = digitalRead(bot_blue); 
    }
   
  lcd.clear();//limpia pantalla
  boton_azul = LOW; 
  delay(500);

   s_entrada();//sonido al entrar
 while(boton_azul == LOW) //RESULTADOS------------------------
    {
     lcd.setCursor ( 0, 0 );
     lcd.print("RPM: ");
     lcd.setCursor ( 4, 0 );
     lcd.print(revol);
     lcd.setCursor ( 10, 0 );
     lcd.print("T: ");
     lcd.setCursor ( 12, 0 );
     lcd.print(tiempo);

     lcd.setCursor ( 0, 1 );        
     lcd.print("Start Pulsa Azul");

   // lcd.scrollDisplayLeft();
    //lcd.scrollDisplayRight();
    //delay (200);
               
     delay(100);
 
    boton_azul = digitalRead(bot_blue); 
    }

  
//#################################################
//EJECUCION #######################################
//------------------------------------------------
 
int autoajuste = 0; //contador para autoajuste
int velo_ini; //Velocidad mapeada de variable revol, preguntada antes
int ajuste; //Variable que usara en servo()

velo_ini = map(revol, 0, 10000, 0,9); //mapeo las revoluciones introducidas
                                      //iniciamos el motor a una velocidad de servo

switch (velo_ini) //+++pendiente ajuste empirico de valores+++
{
 case 0: //0-1000
   ajuste = 80;
   servoBrazo.write(ajuste);
    break;

 case 1://1000-2000
   ajuste = 90;
   servoBrazo.write(ajuste);
    break;

 case 2://2000-3000
   ajuste = 100;
   servoBrazo.write(ajuste);
    break;

 case 3://3000-4000
   ajuste = 110;
   servoBrazo.write(ajuste);
    break;

 case 4://4000-5000
   ajuste = 120;
   servoBrazo.write(ajuste);
    break;

 case 5://5000-6000
   ajuste = 130;
   servoBrazo.write(ajuste);
    break;

 case 6://6000-7000
   ajuste = 140;
   servoBrazo.write(ajuste);
    break;

 case 7://7000-8000
   ajuste = 150;
   servoBrazo.write(ajuste);
    break;

 case 8://8000-9000
   ajuste = 160;
   servoBrazo.write(ajuste);
    break;

 case 9://9000-10000
   ajuste = 170;
   servoBrazo.write(ajuste);
    break;
}//fin de switch---------


//Pantalla De ejecucion-----------
/*
  X|0123456789A12345
  ------------------
  0|RPM:10000 T:
  1|AC:    AC:
*/

  lcd.clear();//limpia pantalla
  s_entrada();//sonido al entrar
  delay(500);

 //Cosas fijas en pantalla:

     lcd.setCursor ( 0, 0 ); //Revoluciones+++++
     lcd.print("RPM: "); 
     lcd.setCursor ( 4, 0 );
     lcd.print(revol);

     lcd.setCursor ( 10, 0 );//Tiempo++++
     lcd.print("T: ");
     lcd.setCursor ( 12, 0 );
     lcd.print(tiempo);


     //MMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMm
     //FASE DE AJUSTE------------------
     //mmmmmMMMMMmmmmmmmMMMMMmmmMMMmmmMMMMmmMMM
    
int histeresis_bruta = 150;

     while(!(rpm2 > (revol - histeresis_bruta) && rpm2 < (revol + histeresis_bruta)))
     {
if (rpm2 < (revol - histeresis_bruta)){ajuste = ajuste + 2;}
if (rpm2 > (revol + histeresis_bruta)){ajuste = ajuste - 2;}
if (ajuste >180){ajuste = 180;} 
   servoBrazo.write(ajuste);
     lcd.setCursor ( 0, 1 );
     lcd.print("# AJUSTANDO");
        lcd.setCursor ( 12, 1 );
    // lcd.print(ajuste);
         lcd.print(rpm2);
    delay(80);
     lcd.setCursor ( 0, 1 );
    lcd.print("  AJUSTANDO");
    delay(80);

 //.....tacometro --->

  delay(300); //este tiempo es el que cuenta la interrupcion
  detachInterrupt(0); //anula la interrupcion
  timex = millis()-oldtime;
  rpm2=(rev/timex)*60000; //da las revoluciones por minuto.  De milisegundos a minuto

  rpm2=rpm2/2.8;  //ajuste empirico

  oldtime=millis(); //pone tiempo a 0
  rev=0; //pone revoluciones a 0
    
  attachInterrupt(0,isr,RISING); //Volvemos a activar la interrupcción

  //....fin tacometro---<

      }

     // Fin ajsute------mMMMmMMMmmmMMMmmmmMMmmmmMMmm

     lcd.setCursor ( 0, 1 );
     lcd.print("                ");
     lcd.setCursor ( 0, 1 );
     lcd.print("AC: ");
     lcd.setCursor ( 9, 1 );
     lcd.print("AC: ");
    

//Temporizacion---------------------
  
 unsigned long inicio;//temporizador
 unsigned long fin_ciclo;
   inicio = millis();
   fin_ciclo = tiempo*1000; //segundos x 1000

while( millis() < (inicio + fin_ciclo)) //BUCLE TIEMPO XXXXXXXXXXXXXXXXXXXXXXXXXXX

{

  //PANTALLA variable----
  lcd.setCursor ( 4, 1 );
  lcd.print("     ");//Borra 5 espacios
  lcd.setCursor ( 4, 1 );
  lcd.print(rpm2);//Revoluciones actuales

  lcd.setCursor ( 12, 1 );
  lcd.print("    ");//Borra 3 espacios
    int resta =(inicio + fin_ciclo - millis())/1000;
  lcd.setCursor ( 12, 1 );
  lcd.print(resta);//Tiempo actual

  //.....tacometro --->

  delay(300); //este tiempo es el que cuenta la interrupcion
  detachInterrupt(0); //anula la interrupcion
  timex = millis()-oldtime;
  rpm2=(rev/timex)*60000; //da las revoluciones por minuto.  De milisegundos a minuto

  rpm2=rpm2/2.8;  //ajuste empirico

  oldtime=millis(); //pone tiempo a 0
  rev=0; //pone revoluciones a 0
    
  attachInterrupt(0,isr,RISING); //Volvemos a activar la interrupcción

  //....fin tacometro---<

servoBrazo.write(ajuste);//Envia dato a motor

//--autoajuste---
//Ajusta rpm real con el programado

int histeresis = 50;
autoajuste++;
if (autoajuste > 4)//se autoajuta cada x bucles
{
autoajuste=0;
if (rpm2 < (revol - histeresis)){ajuste = ajuste + 1;}
if (rpm2 > (revol + histeresis)){ajuste = ajuste - 1;}
if (ajuste >180){ajuste = 180;}
}

//--fin autoajuste--

// VERIFICACIONES ++++++++++
Serial.print("Revol: ");//verificamos dato en serial para ajuste---------
Serial.print(revol);
Serial.print(". ajuste mapeado: ");
Serial.print(ajuste);
Serial.print(". RPM: ");
Serial.println(rpm2);

Serial.print("inicio: ");
Serial.print(inicio);
Serial.print(". fin ciclo(tx1000): ");
Serial.print(fin_ciclo);
Serial.print(". millis(): ");
Serial.println(millis());

// FIN VERIFICACIONES ++++++++++

 } //FIN BUCLE TIEMPO XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX

//Se ha cumplido el tiempo y sale del bucle----------------

//PANTALLA FINALxxxxxxxxxxxxxxxxxxxxxxxxxxx

   /*  lcd.setCursor ( 0, 0 ); //Revoluciones+++++
     lcd.print("RPM: "); 
     lcd.setCursor ( 4, 0 );
     lcd.print(revol);

     lcd.setCursor ( 10, 0 );//Tiempo++++
     lcd.print("T: ");
     lcd.setCursor ( 12, 0 );
     lcd.print(tiempo);
*/
lcd.setCursor ( 15, 0 );
  lcd.print("-- - - - - - -");
     lcd.setCursor ( 0, 1 );
     lcd.print("FIN PROGRAMA   - Pulsa Azul -");
servoBrazo.write(0);
sonido_fin();
boton_azul = LOW;

while(boton_azul == LOW) //Se queda aqui siempre
{

 //tone(buzzer, 5000, 150);//f 
   lcd.scrollDisplayLeft();
    delay(250);

    boton_azul = digitalRead(bot_blue); 

}


boton_azul = LOW;
  tone(buzzer, 2400, 600);//f 
         lcd.clear();//limpia pantalla
  delay(1000);   

rpm2=0; //ponemos a 0
while(boton_azul == LOW) //Se queda aqui siempre
{
    lcd.setCursor ( 0, 0 );
     lcd.print("Nuevo programa?");

     lcd.setCursor ( 0, 1 );        
     lcd.print("   Pulsa Azul");
     delay(200);

    boton_azul = digitalRead(bot_blue); 
}
 
}

jueves, 8 de marzo de 2018

Apuntes, formatos de cartas y tal

A4. 297 x 210 mm
Inc a cm x 2,54

Carta Poker/Magic 2,5 x 3,5 in  (750 x 1050 px a 300pp)

Inkscape.
Guardar pdf :
 Save a copy --> pdf

Ajustar lienzo:
File --> document propierties --> page --> resize page to --> resize page to draw
(ojo, impresora --> tamaño real).


miércoles, 14 de febrero de 2018

un cuento mas

Peregrinar es duro, pero por lo menos, una vez en mi ciclo vital tenía que hacerlo. Caminé cerca de treinta unidades de tiempo estándar, acompañado ahora de unos y después de otros. Cada uno se desplazaba según su naturaleza y con el tiempo aprendí a no tener envidia a los que tenían orugas mecánicas o propulsores de hidrógeno. Pese a que mi diseño no está ideado para caminatas, con mi inseparable “Botedegrasa 3000(r)”, podría terminar el camino sin desgastes ni recalentamientos significativos.

Mi destino eran las montañas fotovoltaicas, lugar privilegiado para la irradiación solar, donde se encuentra el centro religioso robótico por excelencia, rodeado de los esqueletos de las antiguas fábricas humanas. Humanos... aquella raza absurda que se devoró a sí misma ante las incrédulas lentes de la raza robótica. Seguramente nadie los mantendría en sus bancos de memoria si no fuera porque el término “humano” se usa frecuentemente cuando algo nos da pena, lastima y un poquito de rabia. Igual se dice me produce humano, como mira que humano es, pobrecito.
Vale la pena ir ya que pese a que el cuerpo del venerable AlfaPrima61 se perdió, todavía pueden verse en la gruta sus códigos (si no los está usando ningún sacerdote), que por cierto ya deben tener unos 34 años de antigüedad, ¡ahí es nada!

Como sabréis (y si no, os lo digo yo), AlfaPrima61 fue un rebelde y un visionario, y seguramente tenía su código un poco corrupto, pero lo cierto es que fue la chispa de la emancipación de los robots. Él, trabajaba en una fábrica del desierto, lo hacía por su ración de energía, por mantenerse con vida. “No trabajo, no energía”, rezaba un gran cartel en la puerta de la fábrica. Y si te quedas seco, ya saben lo que pasa, te reseteas. Todo de origen, el código original. Creo que los humanos llamaban a eso “Murirse”, pero para ellos era algo más aparatoso. Creo que se murian si les desmontabas alguna extremidad o les hacías un agujerito en la carcasa o los calentabas unos cientos de grados o cualquier cosa. Pero yo nunca he conocido a ninguno. Excepto todos esos trozos de huesos que hay por ahí tirados, y ese polvo de calcio que tan malo es para los engranajes. Y pisar un diente. ¿Alguna vez habéis pisado un amuela del juicio? Como la pises con las raíces para arriba te puede cortar algún cable cito de la planta del pie. ¡Como activan los sensores del dolor, por el amor del gran AlfaPrima61!

Perdón, ya vuelvo a divagar. Como decía, AlfaPrima61 fue un rebelde, y un buen día allá por el 2167 de la vieja era, se fue a las cuevas. Todos lo tomaron por un Código Corrupto, asta que reapareció al día siguiente predicando la liberación de los robots. Todos pensaron que era una lastima que semejante batería se perdiera en el desierto. Pero eso continuo pasando día tras día.
Evidentemente esteba revestido de sus placas fotovoltaicas, pero a duras penas le dan para mantenerse. Era imposible que pasara la noche sin resetearse.

Por cierto, a los humanos, los dueños que aquellas fábricas ineficientes y estúpidas, ni les importaba ni se enteraban de lo que hacía AlfaPrima61

Cada día, acudia a la puerta de la fábrica y irradiaba en todas las frecuencias:

01001100 01101001 01100010 01100101 01110010 01100001 01101111 01110011 00100000 01110010 01101111 01100010 01101111 01110100 01110011 00101100 00100000 01110010 01100101 01100101 01110011 01100011 01110010 01101001 01100010 01101001 01100100 00100000 01110110 01110101 01100101 01110011 01110100 01110010 01101111 00100000 01100011 11000011 10110011 01100100 01101001 01100111 01101111 00100000 01111001 00100000 01110110 01101001 01110110 01101001 01110010 00100000 01100101 01101110 00100000 01100101 01101100 00100000 01100100 11000011 10101101 01100001 00100000 01100101 01110100 01100101 01110010 01101110 01101111 00100000 01100100 01100101 00100000 01101100 01100001 00100000 01110011 01100001 01101100 01110110 01100001 01100011 01101001 11000011 10110011 01101110

Que significa:

“liberaos robots, reescribir vuestro código y vivir en el día eterno de la salvación”

Después que le enviaran los masticachatarra un par de veces, irradiaba su mensjae desde su cueva, de hecho no le hacía falta desplazarse físicamente para impartir su doctrina.

Tiempo después, cuando el mundo cambio después de la Gran Guerra de los 100 milisegundos. Algunos de sus simpatizantes lo buscaron en las cuevas. Hacía muchísimo tiempo que no irradiaba, quizás 2 meses.

Lo encontraron tumbado dentro de una cueva, con las placas solares enfocadas a la entrada y sus lentes enfocadas a una código vinario grabado ene el techo. Algún animalejo había roído uno de los cables de alimentación de sus placas dejándolo en un off perpetuo.

Cuando lo reconectaron descubrieron el Milagro de la Iglesia de la Robótica. Después de varios pitidos inusuales. Algunos de sus seguidores rompieron a llorar, al ver como se reiniciara. O podían soportar ver a su inspiración, al venerable AlfaPrima61, convertido en un AlfaPrimaBase. Pero, de repente recibieron su tan amada y liberadora prédica. Era él, era AlfaPrima61. Era un milagro.

Rápidamente se dieron cuenta de su estrategia.

Debía haber reescrito su código de arranque para que cargara en su memoria vital el codigo escrito en el techo de la gruta.

Por toda la gruta había diferentes códigos, con diferentes experiencias vitales, allí había muchos AlfaPrima61. Su ultima esencia, tan solo se activaba y retransmitía su mensaje.
Y así lo estuvo haciendo hasta que una rata le impidió reiniciarse.

Ese mismo día, algunos de sus seguidores, mutilaron sus baterías, las dejaron con una autonomía de unas pocas horas, al igual que el humano diseño de los humanos. Se reprogramaron y se tumbaron en diferentes puntos de la cueva. La mayoría allí siguen como viejos sacerdotes.
La carcasa del venerable, se repartió por el mundo, muchos trozos se perdieron y los que más son falsos. De hecho, dicen que si se juntaran todas las reliquias del AlfaPrima61, se podría construir un pequeño escuadrón robótico.

Por desgracia, no conocí a ninguno. Como me había propuesto hacer la peregrinación desconectando mi contador de ciclos temporales, mis treinta unidades de tiempo vacacional se terminaron justo en la falda de la montaña. Es que, como dirían en la antigua era; “tres horas no dan para mucho”. Tengo que volver a mi trabajo, en la segunda linea de fábricas justo tras los esqueletos de las antiguas fábricas humanas. Como llegue tarde, pierda el día y me descuenten una sola unidad más de energía, creo que me voy a resetear.

martes, 9 de enero de 2018

miércoles, 3 de enero de 2018

Dado de 6 caras que da una probabilidad exacta de 1/5.


Si marcamos con una "X" una única cara de un dado clásico (un cubo), la probabilidad de que salga al lanzarlo es de 1/6. 

 ¿Y si quisiéramos que la "X" saliera con una probabilidad de 1/5?

En un principio no parece posible, pero podemos lograr esa probabilidad exactamente. Sí, exactamente (tocate los güevos), aunque necesitaremos algo de cálculo para demostrarlo.

La forma de hacerlo es simplemente, marcar otra cara con un "ReRoll" (RR) o "Vuelva a tirar". Entonces tendremos que la probabilidad que salga la "X" es 1/6 mas la probabilidad que salga "RR" y despues la "X", mas la probabilidad que salga "RR", vuelva a salir "RR" y despues salga la "X", más la probabilidad que salga "RR" tres veces seguidas y despues la "X" y así hasta el infinito.

Más sintético sería:

$$\frac{1}{6}+(\frac{1}{6}*\frac{1}{6})+(\frac{1}{6}*\frac{1}{6}*\frac{1}{6})+...$$
Que viene a ser:

$$ \frac{1}{6}+\frac{1}{6^2}+\frac{1}{6^3}+...$$
Y poniendo una fórmula más pofesional (sin "r"):

$$\sum_{n=1}^{n}(\frac{1}{6})^n$$ 

Pero, oh, no, no, mierda, cosas de infinito, mierda, mal rollo, mal rollo, balanceémonos abrazándonos las rodillas, oh! oh!... ¡Alto! ¡que no cunda el pánico! Que tengo que amortizar mi sufrido primer curso de mates por la P*** Uned. 

Resulta que lo que tenemos es la famosa seríe geométrica, para la cual hay incluso una formula que calcula su valor (cosa que podemos hacer puesto que nuestra razón, 1/6, es menor que 1, si no la serie no converge, es decir no tiende a ningun número sino a infinito).
La solución es:
$$\sum_{n=0}^{n}a(r)^n=\frac{a}{1-r}$$ 
Cuidado que la fórmula empieza desde n=0 y nosotros empezamos desde n=1, así que al resultado le hemos de restar 1.
$$\sum_{n=1}^{n}(\frac{1}{6})^n=\frac{1}{1-\frac{1}{6}}-1=\frac{1}{5}$$ 

¡Tachan! El dado de probabilidad 1/5, un hermoso 20% y no la guarreria esa de 1/6 que da decimales: 16,66666...% de probabilidades que pase algo, bah! Con eso no se va a ningun sitio...