Ответ 1
Это можно сделать, обернув массив в struct
. Вы можете включить поле для размера массива, чтобы вам не нужно явно передавать этот параметр. Этот подход имеет преимущество в том, чтобы избежать дополнительных распределений памяти, которые впоследствии должны быть освобождены.
C уже передает аргументы функции по значению, но идентификаторы массива распадаются на указатели в большинстве выражений и, в частности, на вызовы функций. Тем не менее struct
не распадаются на указатели и передаются по значению функции, что означает, что копия исходной структуры и всего ее содержимого видна в области функции. Если struct
содержит массив, это также копируется. Обратите внимание, что если вместо struct
содержится, например, указатель на int
для динамического массива, тогда указатель копируется, когда struct
передается функции, но на ту же память ссылаются как копия, так и исходный указатель. Этот подход основан на struct
, содержащем фактический массив.
Также обратите внимание, что a struct
не может содержать элемент с неполным типом и поэтому не может содержать VLA. Здесь я определил глобальную константу MAX_ARR
равным 100, чтобы предоставить некоторое пространство для обработки массивов разного размера с тем же типом struct
.
Вы также можете вернуть struct
из функции. Я включил пример, который изменяет Array
struct
, который передается в функцию, и возвращает измененную struct
, которая должна быть назначена другому Array
struct
в вызывающей функции. Это приводит к тому, что вызывающий абонент имеет доступ как к оригиналу, так и к преобразованным массивам.
#include <stdio.h>
#define MAX_ARR 100
struct Array {
size_t size;
int array[MAX_ARR];
};
void print_array(struct Array local_arr);
void func(struct Array local_arr);
struct Array triple(struct Array local_arr);
int main(void)
{
struct Array data = {
.size = 10,
.array = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 }
};
struct Array transformed_data;
func(data);
transformed_data = triple(data);
printf("Original\n");
print_array(data);
printf("Transformed\n");
print_array(transformed_data);
return 0;
}
void print_array(struct Array local_arr)
{
for (size_t i = 0; i < local_arr.size; i++) {
printf("%5d", local_arr.array[i]);
}
putchar('\n');
}
void func(struct Array local_arr)
{
for (size_t i = 0; i < local_arr.size; i++) {
local_arr.array[i] *= 2;
}
printf("Modified\n");
print_array(local_arr);
}
struct Array triple(struct Array local_arr)
{
for (size_t i = 0; i < local_arr.size; i++) {
local_arr.array[i] *= 3;
}
return local_arr;
}
Выход программы:
Modified
2 4 6 8 10 12 14 16 18 20
Original
1 2 3 4 5 6 7 8 9 10
Transformed
3 6 9 12 15 18 21 24 27 30