Что за пустота * указателей на функции? - PullRequest
0 голосов
/ 05 мая 2020

Я пытаюсь скомпилировать старый код.

В зависимости от компилятора я получаю это предупреждение / ошибку, когда пытаюсь назначить указатель функции на void* указатель:

warning: a value of type "double (*)(double, double)" cannot be assigned to an entity of type "void *"
error: invalid conversion from ‘double (*)(double, double)’ to ‘void*’

Я думаю, что старый код, используемый для компиляции старый компилятор, но я понимаю, что код недопустим и не должен компилироваться. Мне было интересно, есть ли void* для функций. Я пробовал это до сих пор:

double sum(double a, double b){return a+b;}

typedef double(*dDd)(double, double);
typedef void(*vFun)(void);
dDd   funPtr  = sum;  // compiles and works
void* vFunPtr = sum;  // does not compile   
vFun  vFun_p  = sum;  // does not compile   

, но он не компилируется.

Как это исправить? Я был бы рад, если бы также было обобщение void* на функции.

Ответы [ 3 ]

4 голосов
/ 05 мая 2020

Что такое void * указателей на функции?

В каком-то смысле: все указатели на функции.

Особенность указателя на void заключается в том, что он может указывать к любому объекту, и любой указатель объекта может быть преобразован в указатель на void и обратно, что дает исходный указатель.

Все указатели на функции могут быть преобразованы в другие указатели на типы функций и преобразованы обратно, давая исходное значение.


Другим способом: не существует аналогичного типа указателя для указателей на функции в том смысле, что нет такого типа указателя, в который все типы указателей на функции неявно преобразовывались бы в так же, как объект указатели неявно конвертируются в void*.


Как я могу это исправить?

Конвертируйте указатель явно, если вам нужно, используя приведение. Используйте reinterpret_cast в C ++.

PS Преобразование в void* не гарантируется для работы во всех системах и, следовательно, не является универсальной переносимой. Он «условно поддерживается» по стандарту C ++. Гарантированно работает в системах, соответствующих POSIX.

3 голосов
/ 05 мая 2020

Не существует разработанного универсального типа c для указателей на функции. Однако для этого можно использовать любой тип указателя на функцию. Стандарт C говорит, что любой указатель функции может быть преобразован в любой тип указателя функции. (Конечно, использование преобразованного указателя для вызова функции определяется только в том случае, если тип, используемый для вызова, совместим с фактическим определением функции.)

1 голос
/ 05 мая 2020

В C,

A void* можно без проблем преобразовать в / из в объект указатель.

sum как в void* vFunPtr = sum; не преобразуется в указатель объекта, а в указатель на функцию.

Указатель на функцию и void * могут иметь разные размеры. Приведение указателя функции к void* может привести к потере информации. Сродни some_int = some_long;. Информация может быть потеряна.

vFun vFun_p = sum; требует приведения типа, но в остальном работает: vFun vFun_p = (vFun) sum;.

void* не является универсальным указателем типом указателя.

...