Fixed minor bugs and added documentation for big integers
This commit is contained in:
2
.github/workflows/clang-build.yml
vendored
2
.github/workflows/clang-build.yml
vendored
@@ -12,7 +12,7 @@ jobs:
|
|||||||
|
|
||||||
- name: Build Datum
|
- name: Build Datum
|
||||||
run: |
|
run: |
|
||||||
make clean all
|
make clean all CC=clang
|
||||||
|
|
||||||
- name: Run unit tests
|
- name: Run unit tests
|
||||||
run: |
|
run: |
|
||||||
|
|||||||
92
docs/bigint.md
Normal file
92
docs/bigint.md
Normal file
@@ -0,0 +1,92 @@
|
|||||||
|
# BigInt Technical Details
|
||||||
|
In this document you can find a quick overview of the technical
|
||||||
|
aspects (internal design, memory layout, etc.) of the `BigInt` data structure.
|
||||||
|
|
||||||
|
`BigInt` is a data type for arbitrary precision arithmetic that supports addition,
|
||||||
|
subtraction, multiplication, division and modulo operations on signed integers of unlimited size. Internally, it uses
|
||||||
|
the `Vector` data structure to represent big numbers using the following layout:
|
||||||
|
|
||||||
|
```
|
||||||
|
Number: 2485795518678991171206065
|
||||||
|
Internally: [ 171206065, 518678991, 2485795 ]
|
||||||
|
/ | \
|
||||||
|
/ | \
|
||||||
|
digit[0] digit[1] digit[2]
|
||||||
|
(LSB) (MSB)
|
||||||
|
```
|
||||||
|
|
||||||
|
That is, each element of the vector stores 9 digits in base $10^9$ using
|
||||||
|
**little-endian order**. Each such digits can therefore store values from `0` up to
|
||||||
|
`999,999,999`.
|
||||||
|
|
||||||
|
This scheme maps to the following structure:
|
||||||
|
|
||||||
|
```c
|
||||||
|
typedef struct {
|
||||||
|
vector_t *digits;
|
||||||
|
bool is_negative;
|
||||||
|
} bigint_t;
|
||||||
|
```
|
||||||
|
|
||||||
|
where the `digits` array stores the representation in base $10^9$ of the big integer
|
||||||
|
and the boolean `is_negative` variable denotes its sign.
|
||||||
|
|
||||||
|
The `BigInt` data structure supports the following methods:
|
||||||
|
|
||||||
|
- `bigint_result_t bigint_from_int(value)`: create a big integer from a primitive `int` type;
|
||||||
|
- `bigint_result_t bigint_from_string(string_num)`: create a big integer from a C string;
|
||||||
|
- `bigint_result_t bigint_to_string(number)`: convert a big integer to a C string;
|
||||||
|
- `bigint_result_t bigint_clone(number)`: clone a big integer;
|
||||||
|
- `bigint_result_t bigint_compare(x, y)`: compare two big integers, returning either `-1`, `0` or `1` if the first is less than, equal than or greater than the second, respectively;
|
||||||
|
- `bigint_result_t bigint_add(x, y)`: add two big integers together in $\mathcal{O}(n)$;
|
||||||
|
- `bigint_result_t bigint_sub(x, y)`: subtract two big integers in $\mathcal{O}(n)$;
|
||||||
|
- `bigint_result_t bigint_prod(x, y)`: multiply two big integers using Karatsuba's algorithm in $\mathcal{O}(n^{1.585})$;
|
||||||
|
- `bigint_result_t bigint_divmod(x, y)`: divide two big integers using *long division* algorithm in $\mathcal{O}(n^2)$, returning both the quotient and the remainder;
|
||||||
|
- `bigint_result_t bigint_mod(x, y)`: computes modulo of two big integers using *long division* algorithm in $\mathcal{O}(n^2)$;
|
||||||
|
- `bigint_result_t bigint_destroy(number)`: delete the big number;
|
||||||
|
- `bigint_result_t bigint_printf(format, ...)`: `printf` wrapper that introduces the `%B` placeholder to print big numbers. It supports variadic parameters.
|
||||||
|
|
||||||
|
As you can see by the previous function signatures, methods that operate on the
|
||||||
|
`BigInt` data type return a custom type called `bigint_result_t` which is defined as
|
||||||
|
follows:
|
||||||
|
|
||||||
|
```c
|
||||||
|
typedef enum {
|
||||||
|
BIGINT_OK = 0x0,
|
||||||
|
BIGINT_ERR_ALLOCATE,
|
||||||
|
BIGINT_ERR_DIV_BY_ZERO,
|
||||||
|
BIGINT_ERR_INVALID
|
||||||
|
} bigint_status_t;
|
||||||
|
|
||||||
|
typedef struct {
|
||||||
|
bigint_t *quotient;
|
||||||
|
bigint_t *remainder;
|
||||||
|
} div_result_t;
|
||||||
|
|
||||||
|
typedef struct {
|
||||||
|
bigint_status_t status;
|
||||||
|
uint8_t message[RESULT_MSG_SIZE];
|
||||||
|
union {
|
||||||
|
bigint_t *number;
|
||||||
|
div_result_t division;
|
||||||
|
int8_t compare_status;
|
||||||
|
char *string_num;
|
||||||
|
} value;
|
||||||
|
} bigint_result_t;
|
||||||
|
```
|
||||||
|
|
||||||
|
Each method that returns such type indicates whether the operation was successful or not
|
||||||
|
by setting the `status` field and by providing a descriptive message on the `message`
|
||||||
|
field. If the operation was successful (that is, `status == BIGINT_OK`), you can either
|
||||||
|
move on with the rest of the program or read the returned value from the sum data type.
|
||||||
|
Of course, you can choose to ignore the return value (if you're brave enough :D) as
|
||||||
|
illustrated in the first part of the README.
|
||||||
|
|
||||||
|
The sum data type (i.e., the `value` union) defines four different variables. Each
|
||||||
|
of them has an unique scope as described below:
|
||||||
|
|
||||||
|
- `number`: result of arithmetical, cloning and creating functions;
|
||||||
|
- `division`: result of `bigint_divmod`;
|
||||||
|
- `compare_status`: result of `bigint_compare`;
|
||||||
|
- `string_num`: result of `bigint_to_string`.
|
||||||
|
|
||||||
@@ -71,5 +71,5 @@ typedef struct {
|
|||||||
Each method that returns such type indicates whether the operation was successful or not by setting
|
Each method that returns such type indicates whether the operation was successful or not by setting
|
||||||
the `status` field and by providing a descriptive message on the `message` field. If the operation was
|
the `status` field and by providing a descriptive message on the `message` field. If the operation was
|
||||||
successful (that is, `status == MAP_OK`), you can either move on with the rest of the program or read
|
successful (that is, `status == MAP_OK`), you can either move on with the rest of the program or read
|
||||||
the returned value from the sum data type. Of course, you can choose to ignore the return value (if you're brave enough :D), as illustrated
|
the returned value from the sum data type. Of course, you can choose to ignore the return value (if you're brave enough :D) as illustrated
|
||||||
in the first part of the README.
|
in the first part of the README.
|
||||||
18
docs/sort.md
18
docs/sort.md
@@ -42,7 +42,7 @@ vector_order_t cmp_int_desc(const void *x, const void *y) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Compile with: gcc main.c src/vector.h
|
* Compile with: gcc main.c src/vector.c
|
||||||
* Output: Before sorting: -8 20 -10 125 34 9
|
* Output: Before sorting: -8 20 -10 125 34 9
|
||||||
* After sorting (ascending order): -10 -8 9 20 34 125
|
* After sorting (ascending order): -10 -8 9 20 34 125
|
||||||
* After sorting (descending order): 125 34 20 9 -8 -10
|
* After sorting (descending order): 125 34 20 9 -8 -10
|
||||||
@@ -55,9 +55,11 @@ int main(void) {
|
|||||||
vector_push(v, &values[idx]);
|
vector_push(v, &values[idx]);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const size_t sz = vector_size(v);
|
||||||
|
|
||||||
// Print unsorted array
|
// Print unsorted array
|
||||||
printf("Before sorting: ");
|
printf("Before sorting: ");
|
||||||
for (size_t idx = 0; idx < vector_size(v); idx++) {
|
for (size_t idx = 0; idx < sz; idx++) {
|
||||||
printf("%d ", *(int*)vector_get(v, idx).value.element);
|
printf("%d ", *(int*)vector_get(v, idx).value.element);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -66,7 +68,7 @@ int main(void) {
|
|||||||
|
|
||||||
// Print sorted array
|
// Print sorted array
|
||||||
printf("\nAfter sorting (ascending order): ");
|
printf("\nAfter sorting (ascending order): ");
|
||||||
for (size_t idx = 0; idx < vector_size(v); idx++) {
|
for (size_t idx = 0; idx < sz; idx++) {
|
||||||
printf("%d ", *(int*)vector_get(v, idx).value.element);
|
printf("%d ", *(int*)vector_get(v, idx).value.element);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -75,7 +77,7 @@ int main(void) {
|
|||||||
|
|
||||||
// Print sorted array
|
// Print sorted array
|
||||||
printf("\nAfter sorting (descending order): ");
|
printf("\nAfter sorting (descending order): ");
|
||||||
for (size_t idx = 0; idx < vector_size(v); idx++) {
|
for (size_t idx = 0; idx < sz; idx++) {
|
||||||
printf("%d ", *(int*)vector_get(v, idx).value.element);
|
printf("%d ", *(int*)vector_get(v, idx).value.element);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -124,7 +126,7 @@ vector_order_t cmp_person_by_name(const void *x, const void *y) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Compile with: gcc main.c src/vector.h
|
* Compile with: gcc main.c src/vector.c
|
||||||
* Output: Sort by age:
|
* Output: Sort by age:
|
||||||
* Name: Marco, Age: 25
|
* Name: Marco, Age: 25
|
||||||
* Name: Alice, Age: 28
|
* Name: Alice, Age: 28
|
||||||
@@ -149,9 +151,11 @@ int main(void) {
|
|||||||
// Sort array by age
|
// Sort array by age
|
||||||
vector_sort(employees, cmp_person_by_age);
|
vector_sort(employees, cmp_person_by_age);
|
||||||
|
|
||||||
|
const size_t sz = vector_size(employees);
|
||||||
|
|
||||||
// Print sorted array
|
// Print sorted array
|
||||||
printf("Sort by age:\n");
|
printf("Sort by age:\n");
|
||||||
for (size_t idx = 0; idx < vector_size(employees); idx++) {
|
for (size_t idx = 0; idx < sz; idx++) {
|
||||||
Employee *p = (Employee*)vector_get(employees, idx).value.element;
|
Employee *p = (Employee*)vector_get(employees, idx).value.element;
|
||||||
printf("Name: %s, Age: %d\n", p->name, p->age);
|
printf("Name: %s, Age: %d\n", p->name, p->age);
|
||||||
}
|
}
|
||||||
@@ -161,7 +165,7 @@ int main(void) {
|
|||||||
|
|
||||||
// Print sorted array
|
// Print sorted array
|
||||||
printf("\nSort by name:\n");
|
printf("\nSort by name:\n");
|
||||||
for (size_t idx = 0; idx < vector_size(employees); idx++) {
|
for (size_t idx = 0; idx < sz; idx++) {
|
||||||
Employee *p = (Employee*)vector_get(employees, idx).value.element;
|
Employee *p = (Employee*)vector_get(employees, idx).value.element;
|
||||||
printf("Name: %s, Age: %d\n", p->name, p->age);
|
printf("Name: %s, Age: %d\n", p->name, p->age);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -64,7 +64,7 @@ Each method that returns such type indicates whether the operation was successfu
|
|||||||
by setting the `status` field and by providing a descriptive message on the `message`
|
by setting the `status` field and by providing a descriptive message on the `message`
|
||||||
field. If the operation was successful (that is, `status == VECTOR_OK`), you can either
|
field. If the operation was successful (that is, `status == VECTOR_OK`), you can either
|
||||||
move on with the rest of the program or read the returned value from the sum data type. Of course, you can choose to
|
move on with the rest of the program or read the returned value from the sum data type. Of course, you can choose to
|
||||||
ignore the return value (if you're brave enough :D), as illustrated in the first part of the README.
|
ignore the return value (if you're brave enough :D) as illustrated in the first part of the README.
|
||||||
|
|
||||||
The documentation for the `vector_sort(map, cmp)` method can be found
|
The documentation for the `vector_sort(map, cmp)` method can be found
|
||||||
in [the following document](/docs/sort.md).
|
in [the following document](/docs/sort.md).
|
||||||
20
src/bigint.c
20
src/bigint.c
@@ -315,7 +315,8 @@ bigint_result_t bigint_clone(const bigint_t *number) {
|
|||||||
cloned->is_negative = number->is_negative;
|
cloned->is_negative = number->is_negative;
|
||||||
|
|
||||||
// Copy digits
|
// Copy digits
|
||||||
for (size_t idx = 0; idx < vector_size(number->digits); idx++) {
|
const size_t sz = vector_size(number->digits);
|
||||||
|
for (size_t idx = 0; idx < sz; idx++) {
|
||||||
vector_result_t get_res = vector_get(number->digits, idx);
|
vector_result_t get_res = vector_get(number->digits, idx);
|
||||||
if (get_res.status != VECTOR_OK) {
|
if (get_res.status != VECTOR_OK) {
|
||||||
vector_destroy(cloned->digits);
|
vector_destroy(cloned->digits);
|
||||||
@@ -546,10 +547,12 @@ bigint_result_t bigint_add_abs(const bigint_t *x, const bigint_t *y) {
|
|||||||
long long carry = 0;
|
long long carry = 0;
|
||||||
size_t idx = 0;
|
size_t idx = 0;
|
||||||
|
|
||||||
while (idx < vector_size(x->digits) || idx < vector_size(y->digits) || carry) {
|
const size_t x_size = vector_size(x->digits);
|
||||||
|
const size_t y_size = vector_size(y->digits);
|
||||||
|
while (idx < x_size || idx < y_size || carry) {
|
||||||
long long partial_sum = carry;
|
long long partial_sum = carry;
|
||||||
|
|
||||||
if (idx < vector_size(x->digits)) {
|
if (idx < x_size) {
|
||||||
vector_result_t get_res = vector_get(x->digits, idx);
|
vector_result_t get_res = vector_get(x->digits, idx);
|
||||||
if (get_res.status != VECTOR_OK) {
|
if (get_res.status != VECTOR_OK) {
|
||||||
vector_destroy(sum->digits);
|
vector_destroy(sum->digits);
|
||||||
@@ -564,7 +567,7 @@ bigint_result_t bigint_add_abs(const bigint_t *x, const bigint_t *y) {
|
|||||||
partial_sum += *x_digit;
|
partial_sum += *x_digit;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (idx < vector_size(y->digits)) {
|
if (idx < y_size) {
|
||||||
vector_result_t get_res = vector_get(y->digits, idx);
|
vector_result_t get_res = vector_get(y->digits, idx);
|
||||||
if (get_res.status != VECTOR_OK) {
|
if (get_res.status != VECTOR_OK) {
|
||||||
vector_destroy(sum->digits);
|
vector_destroy(sum->digits);
|
||||||
@@ -643,7 +646,9 @@ bigint_result_t bigint_sub_abs(const bigint_t *x, const bigint_t *y) {
|
|||||||
|
|
||||||
long long borrow = 0;
|
long long borrow = 0;
|
||||||
|
|
||||||
for (size_t idx = 0; idx < vector_size(x->digits); idx++) {
|
const size_t x_size = vector_size(x->digits);
|
||||||
|
const size_t y_size = vector_size(y->digits);
|
||||||
|
for (size_t idx = 0; idx < x_size; idx++) {
|
||||||
vector_result_t x_get_res = vector_get(x->digits, idx);
|
vector_result_t x_get_res = vector_get(x->digits, idx);
|
||||||
if (x_get_res.status != VECTOR_OK) {
|
if (x_get_res.status != VECTOR_OK) {
|
||||||
vector_destroy(difference->digits);
|
vector_destroy(difference->digits);
|
||||||
@@ -657,7 +662,7 @@ bigint_result_t bigint_sub_abs(const bigint_t *x, const bigint_t *y) {
|
|||||||
int *x_digit = (int*)x_get_res.value.element;
|
int *x_digit = (int*)x_get_res.value.element;
|
||||||
long long partial_difference = *x_digit - borrow;
|
long long partial_difference = *x_digit - borrow;
|
||||||
|
|
||||||
if (idx < vector_size(y->digits)) {
|
if (idx < y_size) {
|
||||||
vector_result_t y_get_res = vector_get(y->digits, idx);
|
vector_result_t y_get_res = vector_get(y->digits, idx);
|
||||||
if (y_get_res.status != VECTOR_OK) {
|
if (y_get_res.status != VECTOR_OK) {
|
||||||
vector_destroy(difference->digits);
|
vector_destroy(difference->digits);
|
||||||
@@ -1074,7 +1079,8 @@ bigint_result_t bigint_shift_left(const bigint_t *num, size_t n) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Copy back original digits
|
// Copy back original digits
|
||||||
for (size_t idx = 0; idx < vector_size(num->digits); idx++) {
|
const size_t num_size = vector_size(num->digits);
|
||||||
|
for (size_t idx = 0; idx < num_size; idx++) {
|
||||||
vector_result_t get_res = vector_get(num->digits, idx);
|
vector_result_t get_res = vector_get(num->digits, idx);
|
||||||
if (get_res.status != VECTOR_OK) {
|
if (get_res.status != VECTOR_OK) {
|
||||||
vector_destroy(shifted->digits);
|
vector_destroy(shifted->digits);
|
||||||
|
|||||||
@@ -3,7 +3,7 @@
|
|||||||
|
|
||||||
#define RESULT_MSG_SIZE 64
|
#define RESULT_MSG_SIZE 64
|
||||||
|
|
||||||
// Big numbers numerical base (10^9)
|
// Numerical base (10^9)
|
||||||
#define BIGINT_BASE 1000000000
|
#define BIGINT_BASE 1000000000
|
||||||
// Each digit stores values from 0 to 999,999,999
|
// Each digit stores values from 0 to 999,999,999
|
||||||
#define BIGINT_BASE_DIGITS 9
|
#define BIGINT_BASE_DIGITS 9
|
||||||
|
|||||||
@@ -134,7 +134,9 @@ void test_vector_sort_int_asc(void) {
|
|||||||
assert(sort_res.status == VECTOR_OK);
|
assert(sort_res.status == VECTOR_OK);
|
||||||
|
|
||||||
const int expected[] = { -7, 1, 4, 6, 12, 25, 25, 71 };
|
const int expected[] = { -7, 1, 4, 6, 12, 25, 25, 71 };
|
||||||
for (size_t idx = 0; idx < vector_size(v); idx++) {
|
|
||||||
|
const size_t sz = vector_size(v);
|
||||||
|
for (size_t idx = 0; idx < sz; idx++) {
|
||||||
int *val = (int*)vector_get(v, idx).value.element;
|
int *val = (int*)vector_get(v, idx).value.element;
|
||||||
assert(*val == expected[idx]);
|
assert(*val == expected[idx]);
|
||||||
}
|
}
|
||||||
@@ -157,7 +159,9 @@ void test_vector_sort_int_desc(void) {
|
|||||||
assert(sort_res.status == VECTOR_OK);
|
assert(sort_res.status == VECTOR_OK);
|
||||||
|
|
||||||
const int expected[] = { 71, 25, 25, 12, 6, 4, 1, -7 };
|
const int expected[] = { 71, 25, 25, 12, 6, 4, 1, -7 };
|
||||||
for (size_t idx = 0; idx < vector_size(v); idx++) {
|
|
||||||
|
const size_t sz = vector_size(v);
|
||||||
|
for (size_t idx = 0; idx < sz; idx++) {
|
||||||
int *val = (int*)vector_get(v, idx).value.element;
|
int *val = (int*)vector_get(v, idx).value.element;
|
||||||
assert(*val == expected[idx]);
|
assert(*val == expected[idx]);
|
||||||
}
|
}
|
||||||
@@ -198,7 +202,9 @@ void test_vector_sort_string(void) {
|
|||||||
assert(sort_res.status == VECTOR_OK);
|
assert(sort_res.status == VECTOR_OK);
|
||||||
|
|
||||||
const char *expected[] = { "world!", "system-programming", "hello", "foo", "embedded", "bar"};
|
const char *expected[] = { "world!", "system-programming", "hello", "foo", "embedded", "bar"};
|
||||||
for (size_t idx = 0; idx < vector_size(v); idx++) {
|
|
||||||
|
const size_t sz = vector_size(v);
|
||||||
|
for (size_t idx = 0; idx < sz; idx++) {
|
||||||
const char *val = *(const char**)vector_get(v, idx).value.element;
|
const char *val = *(const char**)vector_get(v, idx).value.element;
|
||||||
assert(!strcmp(val, expected[idx]));
|
assert(!strcmp(val, expected[idx]));
|
||||||
}
|
}
|
||||||
@@ -208,7 +214,7 @@ void test_vector_sort_string(void) {
|
|||||||
|
|
||||||
// Sort vector with custom data type
|
// Sort vector with custom data type
|
||||||
typedef struct {
|
typedef struct {
|
||||||
const char *name;
|
char name[256];
|
||||||
int age;
|
int age;
|
||||||
} Person;
|
} Person;
|
||||||
|
|
||||||
@@ -257,7 +263,8 @@ void test_vector_sort_struct_by_age(void) {
|
|||||||
{ .name = "Bob", .age = 45 }
|
{ .name = "Bob", .age = 45 }
|
||||||
};
|
};
|
||||||
|
|
||||||
for (size_t idx = 0; idx < vector_size(people); idx++) {
|
const size_t sz = sizeof(expected) / sizeof(expected[0]);
|
||||||
|
for (size_t idx = 0; idx < sz; idx++) {
|
||||||
Person *p = (Person*)vector_get(people, idx).value.element;
|
Person *p = (Person*)vector_get(people, idx).value.element;
|
||||||
assert(!strcmp(p->name, expected[idx].name));
|
assert(!strcmp(p->name, expected[idx].name));
|
||||||
assert(p->age == expected[idx].age);
|
assert(p->age == expected[idx].age);
|
||||||
@@ -295,7 +302,8 @@ void test_vector_sort_struct_by_name(void) {
|
|||||||
{ .name = "Sophia", .age = 45 }
|
{ .name = "Sophia", .age = 45 }
|
||||||
};
|
};
|
||||||
|
|
||||||
for (size_t idx = 0; idx < vector_size(people); idx++) {
|
const size_t sz = vector_size(people);
|
||||||
|
for (size_t idx = 0; idx < sz; idx++) {
|
||||||
Person *p = (Person*)vector_get(people, idx).value.element;
|
Person *p = (Person*)vector_get(people, idx).value.element;
|
||||||
assert(!strcmp(p->name, expected[idx].name));
|
assert(!strcmp(p->name, expected[idx].name));
|
||||||
assert(p->age == expected[idx].age);
|
assert(p->age == expected[idx].age);
|
||||||
|
|||||||
11
usage.c
11
usage.c
@@ -88,7 +88,8 @@ int vector_usage(void) {
|
|||||||
printf("Vector capacity (should be > 5): %zu\n\n", vector_capacity(vector));
|
printf("Vector capacity (should be > 5): %zu\n\n", vector_capacity(vector));
|
||||||
|
|
||||||
// Print the whole vector
|
// Print the whole vector
|
||||||
for (size_t idx = 0; idx < vector_size(vector); idx++) {
|
size_t sz = vector_size(vector);
|
||||||
|
for (size_t idx = 0; idx < sz; idx++) {
|
||||||
vector_result_t get_res = vector_get(vector, idx);
|
vector_result_t get_res = vector_get(vector, idx);
|
||||||
if (get_res.status != VECTOR_OK) {
|
if (get_res.status != VECTOR_OK) {
|
||||||
printf("Cannot retrieve vec[%zu]: %s\n", idx, get_res.message);
|
printf("Cannot retrieve vec[%zu]: %s\n", idx, get_res.message);
|
||||||
@@ -136,7 +137,9 @@ int vector_usage(void) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
printf("Added new elements. Before sort: ");
|
printf("Added new elements. Before sort: ");
|
||||||
for (size_t idx = 0; idx < vector_size(vector); idx++) {
|
|
||||||
|
sz = vector_size(vector);
|
||||||
|
for (size_t idx = 0; idx < sz; idx++) {
|
||||||
vector_result_t sort_get_res = vector_get(vector, idx);
|
vector_result_t sort_get_res = vector_get(vector, idx);
|
||||||
if (sort_get_res.status != VECTOR_OK) {
|
if (sort_get_res.status != VECTOR_OK) {
|
||||||
printf("Cannot retrieve vec[%zu]: %s\n", idx, sort_get_res.message);
|
printf("Cannot retrieve vec[%zu]: %s\n", idx, sort_get_res.message);
|
||||||
@@ -157,7 +160,7 @@ int vector_usage(void) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
printf("After sort in ascending order: ");
|
printf("After sort in ascending order: ");
|
||||||
for (size_t idx = 0; idx < vector_size(vector); idx++) {
|
for (size_t idx = 0; idx < sz; idx++) {
|
||||||
vector_result_t sort_get_res = vector_get(vector, idx);
|
vector_result_t sort_get_res = vector_get(vector, idx);
|
||||||
if (sort_get_res.status != VECTOR_OK) {
|
if (sort_get_res.status != VECTOR_OK) {
|
||||||
printf("Cannot retrieve vec[%zu]: %s\n", idx, sort_get_res.message);
|
printf("Cannot retrieve vec[%zu]: %s\n", idx, sort_get_res.message);
|
||||||
@@ -179,7 +182,7 @@ int vector_usage(void) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
printf("After sort in descending order: ");
|
printf("After sort in descending order: ");
|
||||||
for (size_t idx = 0; idx < vector_size(vector); idx++) {
|
for (size_t idx = 0; idx < sz; idx++) {
|
||||||
vector_result_t sort_get_res = vector_get(vector, idx);
|
vector_result_t sort_get_res = vector_get(vector, idx);
|
||||||
if (sort_get_res.status != VECTOR_OK) {
|
if (sort_get_res.status != VECTOR_OK) {
|
||||||
printf("Cannot retrieve vec[%zu]: %s\n", idx, sort_get_res.message);
|
printf("Cannot retrieve vec[%zu]: %s\n", idx, sort_get_res.message);
|
||||||
|
|||||||
Reference in New Issue
Block a user