2014-02-11 3 views
6

Я работаю над проблемой для моей домашней работы на C++, которая включает указатели. Я не прошу, чтобы кто-то выполнял мою работу, но просто помог понять проблему.Лучшее объяснение функции указателя C++?

Проблема заключается в том, чтобы написать функцию

void sort2(double* p, double* p) //First off I am assuming the second "p" is a typo and  should be a q 

Эта функция будет получить два указателя и сортирует значения, которые они указывают. Например, если вы вызываете sort2(&x, &y), тогда x < = y после вызова.

Что мне интересно, если указатели уже отменяются функцией уже, я просто сравниваю x и y, а не их адреса памяти? Если нет, как мне сравнить адреса памяти?

+2

Почему бы не сравнить их адреса памяти? что вы подразумеваете под «если указатели уже отменяются функцией уже»? – John3136

+0

Вам следует сравнить x и y, а не их адреса. – Beta

ответ

4

Вы передаете адрес в 2х double переменных, так что функция sort2()может своп значение в источнике.

Таким образом, когда функция сортировки называется так:

sort2(&x, &y) 

Функция может получить доступ к адресам памяти вызывающего абонента для x и y и поменять местами значения хранятся там, если это необходимо.

Однако, если функция просто взял двойные параметры, значение, т.е.

void sort2(double p1, double p2) 

тогда, хотя функция может еще сравнить и поменять местами значения вокруг, нет никакого способа, которым sort2() мог пройти ОБЕ новые значения возвращаются к своему вызывающему абоненту с его текущей подписью, поскольку p1 и p2 копируются по значению в стек и будут потеряны при возврате функции.

Функция сортировки осуществляет доступ к значениям переменных указателя путем их удаления, например.

if (*p1 > *p2) { 
    // swap/sort etc. 
    double swap = *p2; 
    *p2 = *p1; 
    *p1 = swap; 
} 

И да, вы правы, то второй p почти наверняка опечатка.

+1

Использование термина 'reference' здесь может быть запутанным. –

+0

@ andrew.punnett спасибо за указание, что из – StuartLC

1

Указатели не являются ссылками. Для сравнения значений, хранящихся в указателях, используется оператор разыменования, который является унарным *. C++ и C использует синтаксис объявления, который имитирует использование. Итак double *p дает нам указание, что *p имеет тип double. Тогда значение *p - это значение объекта double, на которое указывали p. Если p фактически не указывает на действительный double, результат разыменования не определен.

2
void sort2(double* p, double* p) 

Первый. Это не удаление ссылок. Двойной * здесь только для того, чтобы сообщить компилятору, что эта функция получает два указателя, указывающих на двойной тип. Это объявление.

Итак, вы передаете сам указатель на функцию здесь. Адреса памяти хранятся в p и q в sort2.

Надеюсь, что решает вашу проблему.

1

Забудьте о программировании и указателях на секунду, и давайте подумаем о библиотеке. Есть много полок с большим количеством книг. Каждая книга находится в определенных координатах. Например, The Сказка о двух городах может быть на Проход P, Полка 2, Слот 14; аналогичным образом, Jane Eyre может быть на Проход Q, Полка 13, Слот 1. Очевидно, что вы хотите, чтобы книги в библиотеке были хорошо организованы, чтобы их можно было легко найти.

Теперь рассмотрите библиотекаря, которому поручено убедиться, что книги в вышеупомянутых координатах находятся в правильном порядке. Библиотекарь идет к каждой координате, смотрит на названия книг в этих координатах и ​​определяет, какой из них должен идти первым. В нашем случае библиотекарь заметил бы, что с J приходит до T, ей нужно поменять книги.

Ваша домашняя работа, по-видимому, является версией на C++. Функция sort2 имеет два адреса памяти (то есть расположение книг), и она должна удостовериться, что содержимое первого местоположения правильно сравнивается с содержимым второго местоположения. («Сравнительно правильно», как правило, либо «сравнивается меньше», либо «сравнивается больше, чем», в зависимости от того, сортируете ли вы восходящий или нисходящий.)

Как называется sort2, эта часть немного сложнее объяснить , и моя аналогия не работает отлично. Переменные x и y обычно считаются данными (например, содержимым книги), но каждый из них также имеет связанный адрес (например, где находится книга). Если вы наберете x, вы запрашиваете содержимое переменной; если вы наберете &x, вы запрашиваете соответствующий адрес памяти. В отличие от книг, память компьютера постоянно меняется (это, конечно же, причина, почему компьютеры настолько полезны). Таким образом, в этом контексте x и y лучше воспринимать как именованный кусок памяти, а не имена для фактических данных (например, они являются названиями мест размещения книг, а не содержимым книг). Поэтому, когда вы звоните по телефону sort2(&x, &y), адреса операторов четко указывают, что вы используете местоположенияx и y, а не их данные. После разговора адреса x и y не будут изменены, но их содержимое может иметь.

Надеюсь, это поможет!

3

Объявление функции с помощью: void sort2(double *p, double *q) { принимает в двух двойных указателях. Когда вы вызываете функцию следующим образом: sort2(&x, &y) вы не разыскиваете указатели, а ссылаетесь на переменные. Например:

void sort2(double *p, double *q) { 
    some_code; 
} 

int main(int argc, const char *argv[]) { 
    double x = 0.2; 
    double y = 0.4; 
    sort2(&x, &y); //x's and y's addresses in memory are being passed to sort2 
    return 0; 
} 

Для сравнения х и адреса памяти Y после того факта, то вы должны ссылаться на них в каком-то состоянии, как это:

if(&x <= &y) 
    do_something; 
1

В вашей ничтожной sort2 (двойной * р , double * p) вы должны назвать имя параметра иначе, как sort2 (double * ptr1, double * ptr2).

Затем позвоните sort2 (& x, & y);

Внутри sort2 (double * ptr1, double * ptr2) вы можете поменять или отсортировать, что захотите.

Смежные вопросы