Указатели в C ++, Операции с необработанной памятью - PullRequest
0 голосов
/ 19 мая 2018

У меня есть несколько разных вопросов по поводу следующего фрагмента кода, пример, приведенный одним из моих профессоров.

Прежде всего, что такое Thing t {8,15}?Это массив из двух целых чисел, 8 и 15?Или это инициализация значений x и y для t (переменная типа Thing) до 8 и 15 соответственно?Во-вторых, то, что происходит в строке:

std::cout << "n\t = " << place[0] << ", " << place[1];

Мне кажется, что он печатает признаки переменной места, который, на мой взгляд, является указателем на int, указывающим на целочисленные значения вадрес памяти t?

Наконец, что на земле происходит в этой строке:

 int y = *( int *)(( char *)& t + 4);

Здесь я потерялся.Пожалуйста, потерпите меня, изучая указатели и память

Код, которым я занимаюсь:

struct Thing {
int x , y ;
int* getPlaces () {
    return & x ;
}
};

int main () {

Thing t {8 ,15};
int* place = (int *)& t ;
std :: cout << "\nt = " << place [0] << ", " << place [1];
int y = *( int *)(( char *)& t + 4);
std :: cout << "\nt.y = " << y ;
int* location = t . getPlaces ();
location [0] = 17;
std :: cout << "\nt.x = " << t . x ;

}

Ответы [ 2 ]

0 голосов
/ 19 мая 2018

{8,15} - список инициализаторов.Таким образом, Thing t{8,15} является объявлением переменной t типа Thing, инициализированной со значениями 8 и 15. Члены инициализируются с этими значениями в порядке объявления, то есть x = 8 и y = 15.

int* place - это объявление указателя на int, но в C / C ++ указатель всегда также является массивом.Таким образом, вы можете написать place[0] для переменной, на которую указывает place, place[1] для переменной, следующей за ней, и так далее.Проверка границ не проводится, поэтому обязательно знайте, что вы делаете.

(some_type) - приведение (в стиле C).Приведение приводит к тому, что следующее выражение будет интерпретировано определенным образом.В вашем примере &t принимает адрес t.Затем этот указатель должен интерпретироваться как указатель на char (по сути, это означает, что каждый элемент представляет собой один байт).Т.е. когда вы добавляете 4 к этому указателю, вы указываете 4 байта в прошлом.Далее (слева) все это интерпретируется как указатель на int.И, наконец (* слева), все это разыменовывается, давая то, что было найдено по этому адресу, интерпретируемое как int.

Резюме: этот пример предназначен только для обучения.НИКОГДА это не программа в настоящей программе.Код зависит от int, равного 4 байтам, и от способности ЦПУ разрешить int для любого адреса.Это не всегда так.

0 голосов
/ 19 мая 2018
Thing t {8 ,15};

это инициализация т.x и y являются членами t, которые инициализируются в 8 и 15.

place [0], а place [1] напечатает 8 и 15, так как место указано на t в предыдущей строке.

int y = *( int *)(( char *)& t + 4);

t преобразуется в (char *), затем добавляется 4, а затем разыменовывается после приведения к int *.будет напечатано 15.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...