Тонкости прохождения по ссылке в С - PullRequest
1 голос
/ 07 декабря 2011

Я поддерживаю некоторый код C, который был написан человеком, у которого была моя последняя работа. Ситуация возникла в отношении передачи по ссылке. Вот сокращенный, надуманный пример того, с чем я работаю:

static int b;

void SetToTen(int *a){
    b = 10;
    /* >>>>>>>  Need to set a equal to b on this line <<<<<<<< */
return;
}

int main{
    int a = 0;
    SetToTen(&a);
    /* Now a should be equal to 10*/
  . 
  .
  .
return 0;
}

В функции SetToTen я мог бы написать:

*a = b;

OR

a = &b;

Я думаю, что эти два функционально эквивалентны (a будет равно десяти с любым из них.) Но мой вопрос: есть ли какие-то хитрые тонкости, связанные с одним над другим? В частности, если я использую a = & b, значит ли это, что если я буду менять b в будущем, то изменится и a? И разве это не тот случай, если я использую * a = b?

Мысли / Размышления / Комментарии приветствуются.

Ответы [ 2 ]

5 голосов
/ 07 декабря 2011

Они функционально не эквивалентны вообще. Этот код:

*a = b;

разыменовывает a и устанавливает его значение равным значению b. Этот код:

a = &b;

изменяет указатель a , указывая на b . Если вы используете второй фрагмент кода, ничего не произойдет, потому что вы меняете указатель a по значению, он на самом деле не изменит a .

2 голосов
/ 07 декабря 2011
*a = b;

Это правильно.

a = &b;

Это просто копирование адреса в значение.Язык C передает все аргументы по значению.(C ++ имеет понятие ссылок) Если вы хотите изменить аргумент, переданный в функцию, вам нужно передать адрес или массив и изменить значение, к которому относится адрес или член массива.

Itможет быть лучше объявить и определить функцию следующим образом:

void setToTen(int *pa){
    *pa = 10;
}

с этими изменениями от вас:

  1. pa (указатель на a) позволяет избежать путаницы при использованииa в качестве значения в вашей главной функции и a в качестве указателя в SetToTen ()
  2. Нет реальной причины где-либо использовать b, если цель состоит в том, чтобы установить переменную, адрес которой передается в10.
  3. Стиль / синтаксис: в большинстве соглашений C о кодировании используются символы, начинающиеся с нижнего регистра как переменные / методы, и символы, начинающиеся с верхнего регистра как типы.
  4. Стиль / синтаксис: явный оператор returnне требуется, если вы не пытаетесь вернуть значение (ваша функция объявлена ​​недействительной) или если вы хотите вернуть преждевременно до конца функции.

Аналогия: ThЕсть два дома: мистер Смит по адресу: 115 Main St., синего цвета, и мистер Джонс по адресу: 205 Elm St., зеленого цвета.У вас есть лист бумаги с адресом мистера Смита.

*a = b; - это все равно, что раскрашивать дом по адресу на листке бумаги того же цвета, что и дом мистера Джонса.

a = &b; похоже на изменение адреса на листе бумаги, чтобы он стал адресом мистера Джонса;на самом деле это ничего не значит.

...