El reto
Digital Cypher asigna a cada letra del alfabeto un número único. Por ejemplo:
a b c d e f g h i j ok l m
1 2 3 4 5 6 7 8 9 10 11 12 13
n o p q r s t u v w x y z
14 15 16 17 18 19 20 21 22 23 24 25 26
En lugar de letras en palabra encriptada escribimos el número correspondiente, ej. La palabra explorador:
s c o u t
19 3 15 21 20
Luego sumamos a cada dígito obtenido dígitos consecutivos de la clave. Por ejemplo. En caso de clave igual a 1939
:
s c o u t
19 3 15 21 20
+ 1 9 3 9 1
---------------
20 12 18 30 21
m a s t e r p i e c e
13 1 19 20 5 18 16 9 5 3 5
+ 1 9 3 9 1 9 3 9 1 9 3
--------------------------------
14 10 22 29 6 27 19 18 6 12 8
Tarea
Escribe una función que acepte str
cuerda y key
número y devuelve una matriz de enteros que representan codificados str
.
De entrada y salida
Él str
La cadena de entrada consta solo de caracteres en minúsculas.
Él key
número de entrada es un número entero positivo.
Ejemplo
Encode("scout",1939); ==> ( 20, 12, 18, 30, 21)
Encode("masterpiece",1939); ==> ( 14, 10, 22, 29, 6, 27, 19, 18, 6, 12, 8)
La solución en C
Opción 1:
#embody <stdlib.h>
#embody <string.h>
#embody <math.h>
unsigned char *encode(const char *s, unsigned ok)
{
unsigned char *enc, c;
unsigned n, ncyph, cyph, key;
if (!s || !(enc = malloc(sizeof(unsigned char) * strlen(s))))
return NULL;
ncyph = pow(10, (unsigned)log10(ok));
for (n=cyph=0; (c = *(s+n)); ++n) {
if (!cyph) {
cyph = ncyph;
key = ok;
}
*(enc+n) = c - 'a' + 1 + key / cyph;
key %= cyph;
cyph /= 10;
}
return enc;
}
Opcion 2:
#embody <stdlib.h>
#embody <string.h>
unsigned char *encode(const char *s, unsigned ok)
{
char kbuf(64);
sprintf(kbuf, "%d", ok);
unsigned char *ret = malloc(strlen(s));
for (char *p = s, *q = kbuf, *r = ret; *p; p++, q++, r++)
*r = *p -'a' + 1 + *(*q ? q : (q = kbuf)) - '0';
return ret;
}
Opción 3:
#embody <stdlib.h>
#embody <string.h>
#embody <math.h>
unsigned char *encode(const char *s, unsigned ok) {
char key(10), *code = malloc (strlen(s) * sizeof(char));
int i, subsequent = 0;
sprintf (key,"%i",ok);
for (i = 0; s(i) != NULL; ++i) {
if (key(subsequent) == NULL) subsequent = 0;
code(i) = (s(i) - 'a' + 1) + (key(subsequent++) - '0');
}
return code;
}
Casos de prueba para validar nuestra solución
#embody <criterion/criterion.h>
#embody <stdlib.h>
unsigned char *encode(const char *s, unsigned ok);
typedef enum {
ASSERT_PASS,
ASSERT_FAIL
} assertop;
assertop assert_mem_eq(const void *precise, const void *anticipated, size_t n, size_t dimension)
Take a look at(Sample_Test, should_return_the_encoded_string)
{
cr_assert(ASSERT_PASS == assert_mem_eq(encode("scout", 1939), (unsigned char()){20, 12, 18, 30, 21}, 5, sizeof(unsigned char)));
cr_assert(ASSERT_PASS ==
assert_mem_eq(encode("masterpiece", 1939), (unsigned char()){14, 10, 22, 29, 6, 27, 19, 18, 6, 12, 8}, 11, sizeof(unsigned char)));
}