#c #pointers #double-pointer
#c #указатели #двойной указатель
Вопрос:
Как я могу передать адрес двойного указателя другому? У меня есть этот код, и он работает корректно, только если я задаю строку с комментариями. Почему размер отличается?
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main(){
char *s1[]={"this","is","a","test"};
char **s2;
int i;
s2=malloc(sizeof(s1)*sizeof(char *));
s2=s1;
for(i=0;i<sizeof(s2)/sizeof(char *);i )//for(i=0;i<sizeof(s1)/sizeof(char *);i )
printf("%s",*(s2 i));
return 0;
}
Комментарии:
1. Не могли бы вы точно описать, что вы ХОТИТЕ сделать в первую очередь? Кстати, строка
s2=malloc(sizeof(s1)*sizeof(char *));
ничего не делает, поскольку вы задаете s2 следующей строкой.2. @Orka: Я хочу передать адрес s1 в s2, а затем распечатать s2 с помощью цикла for.
Ответ №1:
В прокомментированной строке используется sizeof(char*[4])
, который предположительно в четыре раза больше, чем sizeof(char**)
в раскомментированной строке.
Комментарии:
1. итак, я не могу найти размер s2 с помощью sizeof(). Я должен сделать это вручную?
Ответ №2:
При использовании sizeof
оператора вы получите размер массива (в байтах). Однако при применении к указателю вы получите размер указателя, а не данные, на которые он указывает.
В C нет способа найти эту информацию, поэтому вы должны управлять этим вручную, например, с помощью size
переменной или (как вы уже сделали) использовать размер s1
(который будет работать только до тех пор, пока s1
является массивом).
Ответ №3:
sizeof(s1)
выдает общее количество байтов во внешнем массиве, т.е. размер четырех указателей на массивы строк. На моей машине это дает 16 байт (каждый указатель имеет 32 бита). Ваше объявление для s1 эквивалентно выполнению:
char *s1[4]={"this","is","a","test"};
Вы можете сами увидеть эти результаты sizeof:
printf("sizeof(char[4]) == %dn", sizeof(char*[4])); // == 16
printf("sizeof(char**) == %dn", sizeof(char**)); // == 4
Поскольку s2
это символ **, который фактически является символом * с точки зрения sizeof
функции, sizeof(s2)
дает размер символа *, который на моей машине равен 4 байтам.
Если вы хотите присвоить s2 s1 и распечатать его, попробуйте это:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main(int argc, char* argv[])
{
char *s1[]={"this","is","a","teeeeeeeeeeest"};
char **s2;
s2 = s1;
int numOfElementsInS1 = sizeof(s1)/sizeof(*s1);
for(int i = 0; i < numOfElementsInS1; i )
{
printf("s2[%d] = %sn", i, s2[i]);
}
return 0;
}
…который должен дать:
s2[0] = this
s2[1] = is
s2[2] = a
s2[3] = teeeeeeeeeeest
Если ваша цель здесь — скопировать содержимое s1, тогда вам понадобится что-то вроде этого:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main(int argc, char* argv[])
{
char *s1[]={"this","is","a","teeeeeeeeeeest"};
char **s2;
// Allocate memory for s2 and copy the array contents across
int numOfElementsInS1 = sizeof(s1)/sizeof(*s1);
s2 = (char**)malloc(sizeof(s1));
for(int i = 0; i < numOfElementsInS1; i )
{
size_t bytesInThisString = strlen(s1[i]) 1; // 1 for the string termination
s2[i] = (char*)malloc(bytesInThisString);
memcpy(s2[i], s1[i], bytesInThisString);
}
// Print out s2
for(int i = 0; i < numOfElementsInS1; i )
{
printf("s2[%d] = %sn", i, s2[i]);
}
// Free up the memory
for(int i = 0; i < numOfElementsInS1; i )
{
free(s2[i]);
}
free(s2);
return 0;
}
Ответ №4:
sizeof(s1)
… выдает общее количество байтов..
то, что, по вашему мнению, может быть реализовано следующим образом:
s2=malloc(sizeof(s1)*sizeof(char *));
s2[0] = malloc(sizeof(s1[0])*sizeof(char))
.
.
.
.
n so on