diff --git a/.gitignore b/.gitignore index 1c4c8d5..2ed5d2c 100644 --- a/.gitignore +++ b/.gitignore @@ -3,7 +3,8 @@ *.o *.obj *.out - +*.html +*.gz .idea/ *~ *.DotSettings.user diff --git a/Functional Market.html b/Functional Market.html deleted file mode 100644 index 36c7d30..0000000 --- a/Functional Market.html +++ /dev/null @@ -1,3474 +0,0 @@ - - -
1.0.2 2026-04-06 10:42 2026-04-13 10:42 submit-* (limit: 3 per week) archi-* (limit: 2 per hour) epita-prepa-computer-science-prog-104-p-03-2030-firstname.lastname
-├── functional_market
-│ ├── Fundamentals
-│ │ ├── calculator.c
-│ │ ├── calculator.h
-│ │ ├── crepe_stream.c
-│ │ ├── crepe_stream.h
-│ │ ├── intro.c
-│ │ ├── intro.h
-│ │ ├── toolbox.c
-│ │ └── toolbox.h
-│ └── Proficiencies
-│ ├── list.c
-│ ├── list.h
-│ ├── visitor.c
-│ └── visitor.h
-├── .gitignore
-└── README
-firstname.lastname with your login. .gitignore file is mandatory. Tests folder. .gitignore file:*.a
-*.lib
-*.o
-*.obj
-*.out
-
-.idea/
-*~
-*.DotSettings.user
-#include <stddef.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
- fundamentals/intro.c input to a function pointer computer.int compute(int input, int (*executor)(int));
- int next(int n)
-{
- return n + 1;
-}
-
-#include <stdio.h>
-int main(void)
-{
- int n = 3;
- printf("compute(%d, &next) = %d\n", n, compute(n, &next));
-}
- compute(3, &next) = 4
- name.# name = "Isabelle":
-Hello Isabelle!
-
-# name = "Tom Nook":
-Hi Tom Nook.
-
-# name = "Blathers":
-Good night Blathers!
-
-# name = "Mr. Resetti":
-How are you doing Mr. Resetti?
-
-# Anything else (including NULL):
-I don't know you!
- void (*greet(char *name))(void);
- int main(int argc, char *argv[])
-{
- (void)argc;
- (*greet(argv[1]))();
-}
- $ ./greet Isabelle
-Hello Isabelle!
-$ ./greet Toto
-I don't know you!
- fundamentals/calculator.c if, for, while or switch.operator and put it into your calculator.h.a and b depending on op.enum operation
-{
- ADD,
- SUB,
- MUL,
- DIV,
- MOD,
-};
- int calculator(int a, int b, enum operation op);
- #include <stdio.h>
-int main(void)
-{
- int a = 4;
- int b = 6;
- enum operation op = ADD;
- printf("calculator(%d, %d, %d) = %d\n", a, b, op, calculator(a, b, op));
-}
- calculator(4, 6, 0) = 10
- fundamentals/toolbox.c toolbox.h header file.data itself is allocated on the heap, not its elements.NULL array is treated as an empty array, not an error.data of an array is a void * is to allow any type of element,char * to have an easy access to each byte.char *data = arr->data;
-char *second_element = data + arr->elem_size;
-char *fifth_element = data + 4 * arr->elem_size; // Don't forget array indexes are zero-based
- #include <stddef.h>
-
-typedef int (*comparator)(void *, void *);
-typedef void (*mapper)(void *, void *);
-typedef int (*predicate)(void *);
-typedef void *(*reducer)(void *, void *);
-typedef void (*acceptor)(void *);
-
-struct array
-{
- void *data;
- size_t len;
- size_t elem_size;
-};
- f on every element of arr.acceptor is a function that takes a pointer to an element of the array.void foreach(struct array *arr, acceptor f);
- #include <stdio.h>
-#include <stdlib.h>
-
-void print_int(int *n)
-{
- printf("%d\n", *n);
-}
-
-int main(void)
-{
- struct array arr = {
- .data = calloc(4, sizeof(int)),
- .len = 4,
- .elem_size = sizeof(int),
- };
-
- int *data = arr.data;
- data[0] = 0;
- data[1] = 1;
- data[2] = 2;
- data[3] = 3;
-
- foreach(&arr, (acceptor)&print_int);
-
- free(arr.data);
-}
- 0
-1
-2
-3
- arr sorted according to f.comparator is a function that takes two pointers to elements of the array,arr must change, you MUST return arr.struct array *sort(struct array *arr, comparator f);
- #include <stdio.h>
-#include <stdlib.h>
-
-int reverse(int *a, int *b)
-{
- return *b - *a;
-}
-
-void print_int(int *n)
-{
- printf("%d\n", *n);
-}
-
-int main(void)
-{
- struct array arr = {
- .data = calloc(4, sizeof(int)),
- .len = 4,
- .elem_size = sizeof(int),
- };
-
- int *data = arr.data;
- data[0] = 0;
- data[1] = 1;
- data[2] = 2;
- data[3] = 3;
-
- foreach(sort(&arr, (comparator)&reverse), (acceptor)&print_int);
-
- free(arr.data);
-}
- 3
-2
-1
-0
- arr mapped according to f.mapper is a function that takes two pointers.arr must change, you MUST return arr.arr->data, and free the previous one.output_size is the size of an element after mapping.arr with it!struct array *map(struct array *arr, size_t output_size, mapper f);
- #include <stdio.h>
-#include <stdlib.h>
-
-void next(double *res, int *n)
-{
- *res = *n + 1;
-}
-
-void print_double(double *n)
-{
- printf("%.1lf\n", *n);
-}
-
-int main(void)
-{
- struct array arr = {
- .data = calloc(4, sizeof(int)),
- .len = 4,
- .elem_size = sizeof(int),
- };
-
- int *data = arr.data;
- data[0] = 0;
- data[1] = 1;
- data[2] = 2;
- data[3] = 3;
-
- foreach(map(&arr, sizeof(double), (mapper)&next), (acceptor)&print_double);
-
- free(arr.data);
-}
- 1.0
-2.0
-3.0
-4.0
- arr filtered according to if f is true.predicate is a function that takes a pointer to an element of the array, and returns a value:arr must change, you MUST return arr.struct array *filter(struct array *arr, predicate f);
- #include <stdio.h>
-#include <stdlib.h>
-
-int odd(int *n)
-{
- return *n % 2;
-}
-
-void print_int(int *n)
-{
- printf("%d\n", *n);
-}
-
-int main(void)
-{
- struct array arr = {
- .data = calloc(4, sizeof(int)),
- .len = 4,
- .elem_size = sizeof(int),
- };
-
- int *data = arr.data;
- data[0] = 0;
- data[1] = 1;
- data[2] = 2;
- data[3] = 3;
-
- foreach(filter(&arr, (predicate)&odd), (acceptor)&print_int);
-
- free(arr.data);
-}
- 1
-3
- arr reduced by f.reducer is a function that takes two pointers.void *reduce(struct array *arr, void *start_value, reducer f);
- #include <stdio.h>
-#include <stdlib.h>
-
-int *add(int *res, int *n)
-{
- *res += *n;
- return res;
-}
-
-void print_int(int *n)
-{
- printf("%d\n", *n);
-}
-
-int main(void)
-{
- struct array arr = {
- .data = calloc(4, sizeof(int)),
- .len = 4,
- .elem_size = sizeof(int),
- };
-
- int *data = arr.data;
- data[0] = 0;
- data[1] = 1;
- data[2] = 2;
- data[3] = 3;
-
- int res = 0;
- reduce(&arr, &res, (reducer)&add);
- printf("%d\n", res);
-
- free(arr.data);
-}
- 6
- fundamentals/crepe_stream.c MUST use your previous functions.enum dough
-{
- WHEAT,
- BUCKWHEAT,
-};
-
-enum topping
-{
- NOTHING,
-
- // Sweet
- SUGAR,
- CHOCOLATE,
- WHIPPED_CREAM,
-
- // Savory
- CHEESE,
- MEAT,
- EGG,
-};
-
-struct crepe
-{
- char *name;
- enum dough dough;
- enum topping inside;
- enum topping outside;
- int price;
-};
- <name>: $<price>
-- Made out of <dough>
-- Contains <inside topping> with <outside topping> on top
- void print_menu(struct array *arr);
- #include <stdlib.h>
-
-int main(void)
-{
- struct array arr = {
- .elem_size = sizeof(struct crepe),
- .len = 4,
- .data = calloc(4, sizeof(struct crepe)),
- };
- struct crepe *data = arr.data;
- data[0] = (struct crepe){
- .name = "Dairy",
- .dough = BUCKWHEAT,
- .inside = CHEESE,
- .outside = EGG,
- .price = 5,
- };
- data[1] = (struct crepe){
- .name = "Raclette",
- .dough = BUCKWHEAT,
- .inside = CHEESE,
- .outside = MEAT,
- .price = 8,
- };
- data[2] = (struct crepe){
- .name = "Choco",
- .dough = WHEAT,
- .inside = CHOCOLATE,
- .outside = WHIPPED_CREAM,
- .price = 6,
- };
- data[3] = (struct crepe){
- .name = "Sugary",
- .dough = WHEAT,
- .inside = SUGAR,
- .outside = NOTHING,
- .price = 7,
- };
-
- print_menu(&arr);
-
- free(arr.data);
-}
- Dairy: $5
-- Made out of buckwheat
-- Contains cheese with egg on top
-Raclette: $8
-- Made out of buckwheat
-- Contains cheese with meat on top
-Choco: $6
-- Made out of wheat
-- Contains chocolate with whipped cream on top
-Sugary: $7
-- Made out of wheat
-- Contains sugar with nothing on top
- struct array *sort_by_prices(struct array *arr);
- #include <stdlib.h>
-
-int main(void)
-{
- struct array arr = {
- .elem_size = sizeof(struct crepe),
- .len = 4,
- .data = calloc(4, sizeof(struct crepe)),
- };
- struct crepe *data = arr.data;
- data[0] = (struct crepe){
- .name = "Dairy",
- .dough = BUCKWHEAT,
- .inside = CHEESE,
- .outside = EGG,
- .price = 5,
- };
- data[1] = (struct crepe){
- .name = "Raclette",
- .dough = BUCKWHEAT,
- .inside = CHEESE,
- .outside = MEAT,
- .price = 8,
- };
- data[2] = (struct crepe){
- .name = "Choco",
- .dough = WHEAT,
- .inside = CHOCOLATE,
- .outside = WHIPPED_CREAM,
- .price = 6,
- };
- data[3] = (struct crepe){
- .name = "Sugary",
- .dough = WHEAT,
- .inside = SUGAR,
- .outside = NOTHING,
- .price = 7,
- };
-
- print_menu(sort_by_prices(&arr));
-
- free(arr.data);
-}
- Choco: $6
-- Made out of wheat
-- Contains chocolate with whipped cream on top
-Raclette: $8
-- Made out of buckwheat
-- Contains cheese with meat on top
-Sugary: $7
-- Made out of wheat
-- Contains sugar with nothing on top
-Dairy: $5
-- Made out of buckwheat
-- Contains cheese with egg on top
- struct array *names(struct array *arr);
- #include <stdlib.h>
-
-void print_string(char **str)
-{
- puts(*str);
-}
-
-int main(void)
-{
- struct array arr = {
- .elem_size = sizeof(struct crepe),
- .len = 4,
- .data = calloc(4, sizeof(struct crepe)),
- };
- struct crepe *data = arr.data;
- data[0] = (struct crepe){
- .name = "Dairy",
- .dough = BUCKWHEAT,
- .inside = CHEESE,
- .outside = EGG,
- .price = 5,
- };
- data[1] = (struct crepe){
- .name = "Raclette",
- .dough = BUCKWHEAT,
- .inside = CHEESE,
- .outside = MEAT,
- .price = 8,
- };
- data[2] = (struct crepe){
- .name = "Choco",
- .dough = WHEAT,
- .inside = CHOCOLATE,
- .outside = WHIPPED_CREAM,
- .price = 6,
- };
- data[3] = (struct crepe){
- .name = "Sugary",
- .dough = WHEAT,
- .inside = SUGAR,
- .outside = NOTHING,
- .price = 7,
- };
-
- foreach(names(&arr), (acceptor)&print_string);
-
- free(arr.data);
-}
- Dairy
-Raclette
-Choco
-Sugary
- struct array *vegetarian(struct array *arr);
- #include <stdlib.h>
-
-int main(void)
-{
- struct array arr = {
- .elem_size = sizeof(struct crepe),
- .len = 4,
- .data = calloc(4, sizeof(struct crepe)),
- };
- struct crepe *data = arr.data;
- data[0] = (struct crepe){
- .name = "Dairy",
- .dough = BUCKWHEAT,
- .inside = CHEESE,
- .outside = EGG,
- .price = 5,
- };
- data[1] = (struct crepe){
- .name = "Raclette",
- .dough = BUCKWHEAT,
- .inside = CHEESE,
- .outside = MEAT,
- .price = 8,
- };
- data[2] = (struct crepe){
- .name = "Choco",
- .dough = WHEAT,
- .inside = CHOCOLATE,
- .outside = WHIPPED_CREAM,
- .price = 6,
- };
- data[3] = (struct crepe){
- .name = "Sugary",
- .dough = WHEAT,
- .inside = SUGAR,
- .outside = NOTHING,
- .price = 7,
- };
-
- print_menu(vegetarian(&arr));
-
- free(arr.data);
-}
- Dairy: $5
-- Made out of buckwheat
-- Contains cheese with egg on top
-Choco: $6
-- Made out of wheat
-- Contains chocolate with whipped cream on top
-Sugary: $7
-- Made out of wheat
-- Contains sugar with nothing on top
- int total_price(struct array *arr);
- #include <stdlib.h>
-
-int main(void)
-{
- struct array arr = {
- .elem_size = sizeof(struct crepe),
- .len = 4,
- .data = calloc(4, sizeof(struct crepe)),
- };
- struct crepe *data = arr.data;
- data[0] = (struct crepe){
- .name = "Dairy",
- .dough = BUCKWHEAT,
- .inside = CHEESE,
- .outside = EGG,
- .price = 5,
- };
- data[1] = (struct crepe){
- .name = "Raclette",
- .dough = BUCKWHEAT,
- .inside = CHEESE,
- .outside = MEAT,
- .price = 8,
- };
- data[2] = (struct crepe){
- .name = "Choco",
- .dough = WHEAT,
- .inside = CHOCOLATE,
- .outside = WHIPPED_CREAM,
- .price = 6,
- };
- data[3] = (struct crepe){
- .name = "Sugary",
- .dough = WHEAT,
- .inside = SUGAR,
- .outside = NOTHING,
- .price = 7,
- };
-
- printf("%d\n", total_price(&arr));
-
- free(arr.data);
-}
- 26
- proficiencies/list.c NULL is considered an empty list.typedef void (*acceptor)(void*);
-
-struct list
-{
- void *data;
- struct list *next;
- acceptor print;
- acceptor free;
-};
- l is NULL, don't do anything and return.void push_front(struct list **l, void *data, acceptor p, acceptor f);
- l is NULL or empty, don't do anything and return.void pop_front(struct list **l);
- void do_nothing(void *n)
-{
- (void)n;
-}
-
-void print_long(void *n)
-{
- printf("%ld", (long)n);
-}
-
-void print_int(int *n)
-{
- printf("%d", *n);
-}
-
-int main(void)
-{
- struct list *l = NULL;
- push_front(&l, (void *)18, &print_long, &do_nothing);
- int *on_heap = calloc(1, sizeof(int));
- *on_heap = 42;
- push_front(&l, on_heap, (acceptor)&print_int, &free);
- int on_stack = 4;
- push_front(&l, &on_stack, (acceptor)&print_int, &do_nothing);
- // print_list(l);
- pop_front(&l);
- pop_front(&l);
- pop_front(&l);
-}
- // Nothing
- void print_list(struct list *l);
- void do_nothing(void *n)
-{
- (void)n;
-}
-
-void print_long(void *n)
-{
- printf("%ld", (long)n);
-}
-
-void print_int(int *n)
-{
- printf("%d", *n);
-}
-
-int main(void)
-{
- struct list *l = NULL;
- push_front(&l, (void *)18, &print_long, &do_nothing);
- int *on_heap = calloc(1, sizeof(int));
- *on_heap = 42;
- push_front(&l, on_heap, (acceptor)&print_int, &free);
- int on_stack = 4;
- push_front(&l, &on_stack, (acceptor)&print_int, &do_nothing);
- print_list(l);
- pop_front(&l);
- pop_front(&l);
- pop_front(&l);
-}
- 4 -> 42 -> 18
- l is NULL, don't do anything and return.void destroy_list(struct list **l);
- void do_nothing(void *n)
-{
- (void)n;
-}
-
-void print_long(void *n)
-{
- printf("%ld", (long)n);
-}
-
-void print_int(int *n)
-{
- printf("%d", *n);
-}
-
-int main(void)
-{
- struct list *l = NULL;
- push_front(&l, (void *)18, &print_long, &do_nothing);
- int *on_heap = calloc(1, sizeof(int));
- *on_heap = 42;
- push_front(&l, on_heap, (acceptor)&print_int, &free);
- int on_stack = 4;
- push_front(&l, &on_stack, (acceptor)&print_int, &do_nothing);
- print_list(l);
- destroy_list(&l);
-}
- 4 -> 42 -> 18
- proficiencies/visitor.c ast_node are its operands, there may be 0, 1 or 2 depending on the type.enum node_type
-{
- // 0 operand
- NUM,
-
- // 1 operand
- POS,
- NEG,
-
- // 2 operands
- ADD,
- SUB,
- MUL,
- DIV,
- MOD,
-};
-
-struct ast_node
-{
- int value;
- enum node_type type;
- struct ast_node *children;
-};
-
-typedef void(*visitor)(struct ast_node *);
- MUST NOT use any if, while, for or switch!v on node.void visit(struct ast_node *node, visitor v);
- a as the first operandb as the second operandop as the operatorBinary operators:
-(a op b)
-Unary operators:
-opa
-Number:
-a
- void print_infix(struct ast_node *node);
- int main(void)
-{
- struct ast_node node = {
- .type = MUL,
- .children =
- (struct ast_node[]){
- {
- .type = NUM,
- .value = 6,
- },
- {
- .type = NEG,
- .children =
- (struct ast_node[]){
- {
- .type = NUM,
- .value = 7,
- },
- },
- },
- },
- };
-
- print_infix(&node);
-}
- (6 * -7)
- a as the first operandb as the second operandop as the operatorBinary operators:
-op a b
-Unary operators:
-op a
-Number:
-a
- void print_prefix(struct ast_node *node);
- int main(void)
-{
- struct ast_node node = {
- .type = MUL,
- .children =
- (struct ast_node[]){
- {
- .type = NUM,
- .value = 6,
- },
- {
- .type = NEG,
- .children =
- (struct ast_node[]){
- {
- .type = NUM,
- .value = 7,
- },
- },
- },
- },
- };
-
- print_prefix(&node);
-}
- * 6 - 7
- a as the first operandb as the second operandop as the operatorBinary operators:
-a b op
-Unary operators:
-a op
-Number:
-a
- void print_suffix(struct ast_node *node);
- int main(void)
-{
- struct ast_node node = {
- .type = MUL,
- .children =
- (struct ast_node[]){
- {
- .type = NUM,
- .value = 6,
- },
- {
- .type = NEG,
- .children =
- (struct ast_node[]){
- {
- .type = NUM,
- .value = 7,
- },
- },
- },
- },
- };
-
- print_suffix(&node);
-}
- 6 7 - *
- 1.0.2 ] 2026-04-07 18:00:00 visitor.c > print: specified adding a newline 1.0.1 ] 2026-04-06 19:00:00 Guidelines > Includes: added authorized includes