Что делает ((short *) ((((char *) (& arr [1])) + 8)) [3] = 100; делать? - PullRequest
0 голосов
/ 01 августа 2020
...
    int arr[5];
    arr[3]=128;
    ((short *)((((char *)(&arr[1]))+8))[3]=100;
...

Это часть претенциозного кода.

  1. Что делает

    ((short *)((((char *)(&arr[1])) + 8))[3] = 100
    

    строка? Следующее - моя мысль, предполагая, что char составляет 1 байт, а int - 4 байта.

    arr будет выглядеть как arr[0], arr[1], arr[2], arr[3], arr[4] в памяти с каждым 4 байты. &arr[1] указывает на arr [1]. (char *)(&arr[1]) обрабатывает arr[1] значение 4 байта как char каждый из 1 байта.

  2. Какова функциональная часть (char *)(&arr[1]) и ((char *)(&arr[1])) + 8 по отдельности?

Ответы [ 3 ]

1 голос
/ 01 августа 2020
((short *)((((char *)(&arr[1])) + 8))[3] = 100

&arr[1]:  is the address of the second int in arr (1*sizeof(int) from start).
((char *)(&arr[1])) : converts int address  to a char address
(((char *)(&arr[1])) + 8) : adds 8 bytes to the char address
((short *)((((char *)(&arr[1])) + 8)): converts the char address to a short address
((short *)((((char *)(&arr[1])) + 8))[3]: treats the short address as a beginning of an array of storts and goes to the third element in this array (3 * sizeof(short) bytes).
((short *)((((char *)(&arr[1])) + 8))[3] = 100; : assigns 100


*((short*)(((char*)arr) + 1*sizeof(int) + 8 + 3*sizeof(short))) = 100;

Размер int варьируется в зависимости от процессора, но часто составляет 4 байта. Размер короткого замыкания зависит от процессора, но часто составляет 2 байта.

*((short*)(((char*)arr) + 18)) = 100;
1 голос
/ 01 августа 2020

Давайте разделим его (игнорируя ненужные скобки):

int* p0 = &arr[1];
char* p1 = (char *)p0;
char* p2 = p1 + 8;
short* p3 = (short *)p2;
p3[3] = 100;
  • Ваш массив arr имеет 5-кратное 4-байтовое целое число = блок из 20 байтов.
  • p0 указывает на адрес второго целого числа, поэтому байт с индексом 4.
  • p1 сохраняет p0 как адрес для символов / байтов.
  • p2 увеличивает значение p1 на 8 (символов) = указывает на байт с индексом 12.
  • p3 изменяет p2 на тип указателя 2-байтового (короткого) целого числа.
  • Последняя строка указывает на четвертую короткое (целое) значение, которое означает приращение адреса на 3 * 2 байта = теперь мы находимся в байтовом индексе 18 из arr. Здесь мы присваиваем значение 100 последним двум байтам (индексы 18 и 19) нашей доступной памяти.

Вкратце:

((short *)arr)[9] = 100;

Полный пример:

#include <stdio.h>  // printf

int main(void) {
  // Initialize zero-filled memory
  int arr[5] = {0};
  // Write value 100 to last 2 bytes
  ((short*)arr)[9] = 100;
  // Print memory
  for (int i = 0; i < sizeof(arr) / sizeof(arr[0]); i++)
    printf("%d ", arr[i]);  // 0 0 0 0 6553600
}
0 голосов
/ 01 августа 2020

его можно перевести на:

short *ptr = (short *)(arr + 1 + 8 / sizeof(*arr)); // or &arr[1 + 8 / sizeof(*arr)]
ptr[3] = 100;
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...