Эквивалентность обозначения массива с двойным указателем на C

#c #arrays #pointers

#c #массивы #указатели

Вопрос:

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

 char** argv = malloc(2*sizeof(char*));

//argv[0] == (argv   0), *(argv   0), or (*argv   0)?

//Same way, what would argv[0][0] be equivalent to in terms of *(*(argv  i) j), etc.?
  

Комментарии:

1. Ваш второй комментарий правильный и содержит ответ на первый. Предполагая, конечно, что в вашем коде есть дополнительные malloc вызовы для инициализации двух указателей, которые вы выделили при первом malloc вызове.

2. Не могли бы вы, пожалуйста, помочь мне понять, почему мне нужно malloc дважды? Итак, если я использую malloc для char ** argv, этого недостаточно для char * argv? Мне также нужно malloc для char * argv?

3. argv 0 эквивалентно argv (очевидно). *argv 0 эквивалентно *argv (также очевидно). argv не эквивалентно *argv (очень очевидно).

4. Вы выделили место для двух указателей: 2*sizeof(char*) . Теперь каждый из этих указателей должен указывать на что-то, например, argv[0] = malloc(20); Без дополнительных mallocs , у вас есть одномерный массив указателей. С дополнительным mallocs вы получаете эквивалент двумерного массива char .

5. значит, argv — это то же самое, что argv[0]? и если я выведу argv[0], я получу адрес указателя, на который указывает argv?

Ответ №1:

//argv[0] == (argv 0), *(argv 0), or (*argv 0)?

Ну, здесь оба *(argv 0) и (*argv 0) оба эквивалентны argv[0] . Это можно легко узнать, распечатав выходные данные. Вы можете сделать что-то вроде этого:

 char** argv = malloc(2*sizeof(char*));

for(int i = 0; i < 2; i  ){
    argv[i] = malloc(1);
}

//printing the values:
printf("%p == %pn", argv[0], argv   0);
printf("%p == %pn", argv[0], *(argv   0));
printf("%p == %pn", argv[0], *argv   0);
  

вывод:

 0x8e84018 == 0x8e84008 //not equal
0x8e84018 == 0x8e84018 //same
0x8e84018 == 0x8e84018 //same
  

смотрите здесь полный пример:https://ideone.com/DDXuI9

это неверно в случае, (argv 0) потому что (argv 0) указывает на адрес char** argv самого argv[0] элемента, тогда как указывает на адрес первого элемента char* ) В C