Это не передача по ссылке, это передача по значению, как заявили другие.
Язык Си передается по значению без исключения. Передача указателя в качестве параметра не означает передачу по ссылке.
Правило следующее:
Функция не может изменить фактическое значение параметров.
Давайте попробуем увидеть разницу между скалярными и указательными параметрами функции.
Скалярные переменные
Эта короткая программа показывает передачу по значению с использованием скалярной переменной. param
называется формальным параметром и variable
при вызове функции называется фактическим параметром. Приращение примечания param
в функции не изменяется variable
.
#include <stdio.h>
void function(int param) {
printf("I've received value %d\n", param);
param++;
}
int main(void) {
int variable = 111;
function(variable);
printf("variable %d\m", variable);
return 0;
}
Результат
I've received value 111
variable=111
Иллюзия передачи по ссылке
Мы немного изменили кусок кода. param
указатель сейчас
#include <stdio.h>
void function2(int *param) {
printf("I've received value %d\n", *param);
(*param)++;
}
int main(void) {
int variable = 111;
function2(&variable);
printf("variable %d\n", variable);
return 0;
}
Результат
I've received value 111
variable=112
Это заставляет вас поверить, что параметр был передан по ссылке. Не было. Он был передан по значению, а значение параметра является адресом. Значение типа int было увеличено, и это побочный эффект, который заставляет нас думать, что это был вызов функции передачи по ссылке.
Указатели - передаваемые по значению
Как мы можем показать / доказать этот факт? Ну, может быть, мы можем попробовать первый пример скалярных переменных, но вместо скалярных мы используем адреса (указатели). Посмотрим, может ли это помочь.
#include <stdio.h>
void function2(int *param) {
printf("param's address %d\n", param);
param = NULL;
}
int main(void) {
int variable = 111;
int *ptr = &variable;
function2(ptr);
printf("ptr's address %d\n", ptr);
return 0;
}
Результатом будет то, что два адреса равны (не беспокойтесь о точном значении).
Пример результата:
param's address -1846583468
ptr's address -1846583468
На мой взгляд, это ясно показывает, что указатели передаются по значению. В противном случае ptr
будет NULL
после вызова функции.