2016-10-30 7 views
2

Например, я хотел бы знать, если есть какие-либо существенные различия или хорошая/плохая практикаВ чем разница, передавая непосредственно функцию sizeof() и предыдущую объявленную и инициализированную переменную?

Делать это так:

unsigned int length_addr; 
length_addr = sizeof(cli_addr); 

nbytes = recvfrom(sockfd, buffer, sizeof(buffer), 0, 
        (struct sockaddr *)&cli_addr, &length_addr); 

и таким образом:

nbytes = recvfrom(sockfd, buffer, sizeof(buffer), 0, 
        (struct sockaddr *)&cli_addr, sizeof(cli_addr)); 

ответ

2

Да, есть существенная разница.

  • В первом случае, вы передаете адрес из unsigned int, в основном в insigned int *.

  • Во втором случае вы принимаете решение оператора sizeof, тип size_t.

Это не то же самое.

Это, как и в случае с man page, в основном оба неправильные. Последний аргумент должен быть типа socklen_t *, поэтому лучше придерживаться правильных типов.

+0

Когда вы говорите «оба неправильно», они на 100% неверны? почему первый неверен? Im передает ссылку unsigned int. Аргумент socklen_t * не может быть беззнаковым int? –

+1

@jorgesaraiva, 'socklen_t' является одним из типов, сильно зависящих от размера архитектуры ... поскольку они могут быть реализованы как' signed int' (чтобы допускать отрицательные значения ошибок) как 'unsigned int' (чтобы разрешить большие значения) и 'unsigned long int' (например, в 64-битных архитектурах, 64-битное целое число), чтобы допускать огромные значения. Вам лучше использовать подходящие типы, поскольку они там для вашего удобства. И действительно, больше, если вам нужно наложить указатель на тип, а не на значение. Это распространенная ошибка, которая приводит к многим необнаруженным ошибкам, очень трудно преследовать. –

1

На самом деле разница. Как сказал кто-то, существует большая разница между передачей адреса (первая ситуация) или значением (size_t) (вторая ситуация). Если вы проверите справочную ссылку recvfrom, вы увидите, что последний аргумент является указателем на пространство памяти, размер которого имеет размер sockaddr предыдущего аргумента.

#include <sys/socket.h> 

ssize_t recvfrom(int socket, void *buffer, size_t length, int flags, 
     struct sockaddr *address, socklen_t *address_len); 


/*address_len 
Specifies the length of the sockaddr structure pointed to by the address argument.*/ 

Первый на самом деле правильно, как вы даете на lenght_addr размер cli_addr и затем передать указатель в качестве аргумента. Поэтому он должен работать нормально.