diff --git a/challenges/slugify/solutions/c/function/README.md b/challenges/slugify/solutions/c/function/README.md new file mode 100644 index 0000000..9f89d08 --- /dev/null +++ b/challenges/slugify/solutions/c/function/README.md @@ -0,0 +1,3 @@ +# slugify/c/function + +Created by [@Divlo](https://github.com/Divlo) on 10 November 2021. diff --git a/challenges/slugify/solutions/c/function/character.c b/challenges/slugify/solutions/c/function/character.c new file mode 100644 index 0000000..7b96fc3 --- /dev/null +++ b/challenges/slugify/solutions/c/function/character.c @@ -0,0 +1,33 @@ +#include "character.h" + +#include +#include +#include + +void character_append(char* string, char character) { + size_t length = strlen(string); + string[length] = character; + string[length + 1] = '\0'; +} + +char character_to_lower(char character) { + char ascii_a = 'a'; + char ascii_A = 'A'; + char ascii_Z = 'Z'; + if (character >= ascii_A && character <= ascii_Z) { + return character + (ascii_a - ascii_A); + } + return character; +} + +bool character_is_alphanumeric(char character) { + char ascii_a = 'a'; + char ascii_A = 'A'; + char ascii_z = 'z'; + char ascii_Z = 'Z'; + char ascii_0 = '0'; + char ascii_9 = '9'; + return (character >= ascii_a && character <= ascii_z) || + (character >= ascii_A && character <= ascii_Z) || + (character >= ascii_0 && character <= ascii_9); +} diff --git a/challenges/slugify/solutions/c/function/character.h b/challenges/slugify/solutions/c/function/character.h new file mode 100644 index 0000000..d28e833 --- /dev/null +++ b/challenges/slugify/solutions/c/function/character.h @@ -0,0 +1,31 @@ +#ifndef __CHARACTER__ +#define __CHARACTER__ + +#include + +/** + * @brief Append a character to a string, assuming string points to an array + * with enough space. + * + * @param string + * @param character + */ +void character_append(char* string, char character); + +/** + * @brief Converts the character to lowercase. + * + * @param character + * @return char + */ +char character_to_lower(char character); + +/** + * @brief Checks if the character is alphanumeric. + * + * @param character + * @return bool + */ +bool character_is_alphanumeric(char character); + +#endif diff --git a/challenges/slugify/solutions/c/function/input.c b/challenges/slugify/solutions/c/function/input.c new file mode 100644 index 0000000..c07bb6d --- /dev/null +++ b/challenges/slugify/solutions/c/function/input.c @@ -0,0 +1,19 @@ +#include "input.h" + +#include +#include + +#include "character.h" + +char* input() { + char character; + size_t length = 1; + char* string = malloc(length * sizeof(char)); + *string = '\0'; + while ((character = getchar()) != '\n' && character != EOF) { + length++; + string = realloc(string, length * sizeof(char)); + character_append(string, character); + } + return string; +} diff --git a/challenges/slugify/solutions/c/function/input.h b/challenges/slugify/solutions/c/function/input.h new file mode 100644 index 0000000..d432398 --- /dev/null +++ b/challenges/slugify/solutions/c/function/input.h @@ -0,0 +1,11 @@ +#ifndef __INPUT__ +#define __INPUT__ + +/** + * @brief Read a line from stdin. + * + * @return char* + */ +char* input(); + +#endif diff --git a/challenges/slugify/solutions/c/function/solution.c b/challenges/slugify/solutions/c/function/solution.c new file mode 100644 index 0000000..b9ff7f4 --- /dev/null +++ b/challenges/slugify/solutions/c/function/solution.c @@ -0,0 +1,17 @@ +#include +#include + +#include "character.h" +#include "input.h" +#include "string.h" + +int main() { + char* string = input(); + string = string_trim(string, ' '); + string = string_trim(string, '-'); + string = string_to_lowercase(string); + string = string_slugify(string); + printf("%s\n", string); + free(string); + return EXIT_SUCCESS; +} diff --git a/challenges/slugify/solutions/c/function/string.c b/challenges/slugify/solutions/c/function/string.c new file mode 100644 index 0000000..a5d7f7f --- /dev/null +++ b/challenges/slugify/solutions/c/function/string.c @@ -0,0 +1,70 @@ +#include "string.h" + +#include +#include +#include + +#include "character.h" + +char* string_trim_start(char* string, char character) { + size_t string_length = strlen(string); + char* result = malloc(sizeof(char) * (string_length + 1)); + size_t index_space = 0; + while (string[index_space] == character) { + index_space++; + } + for (size_t index = index_space; index < string_length; index++) { + character_append(result, string[index]); + } + return result; +} + +char* string_trim_end(char* string, char character) { + size_t string_length = strlen(string); + char* result = malloc(sizeof(char) * (string_length + 1)); + size_t index_space = string_length - 1; + while (string[index_space] == character) { + index_space--; + } + for (size_t index = 0; index < index_space + 1; index++) { + character_append(result, string[index]); + } + return result; +} + +char* string_trim(char* string, char character) { + char* result = string_trim_start(string, character); + result = string_trim_end(result, character); + return result; +} + +char* string_to_lowercase(char* string) { + size_t string_length = strlen(string); + char* result = malloc(sizeof(char) * (string_length + 1)); + for (size_t index = 0; index < string_length; index++) { + character_append(result, character_to_lower(string[index])); + } + return result; +} + +char* string_slugify(char* string) { + size_t string_length = strlen(string); + char* result = malloc(sizeof(char) * (string_length + 1)); + int words = 0; + char* current = malloc(sizeof(char) * (string_length + 1)); + for (size_t index = 0; index < string_length; index++) { + if (string[index] == ' ' || (string[index] == '-' && strlen(current) > 0)) { + strcat(result, current); + character_append(result, '-'); + memset(current, 0, sizeof(char) * (string_length + 1)); + words++; + } else { + if (character_is_alphanumeric(string[index])) { + character_append(current, string[index]); + } + } + } + strcat(result, current); + free(current); + return result; +} diff --git a/challenges/slugify/solutions/c/function/string.h b/challenges/slugify/solutions/c/function/string.h new file mode 100644 index 0000000..9088029 --- /dev/null +++ b/challenges/slugify/solutions/c/function/string.h @@ -0,0 +1,44 @@ +#ifndef __STRING__ +#define __STRING__ + +/** + * @brief Removes all `character` from the start of a string. + * + * @param string + * @return char* + */ +char* string_trim_start(char* string, char character); + +/** + * @brief Removes all `character` from the end of a string. + * + * @param string + * @return char* + */ +char* string_trim_end(char* string, char character); + +/** + * @brief Removes all `character` from the start and end of a string. + * + * @param string + * @return char* + */ +char* string_trim(char* string, char character); + +/** + * @brief Converts all the alphabetic characters in a string to lowercase. + * + * @param string + * @return char* + */ +char* string_to_lowercase(char* string); + +/** + * @brief Generate a slug from a string. + * + * @param string + * @return char* + */ +char* string_slugify(char* string); + +#endif