Интересно, если typedef
и #define
одинаковы в c?
Являются ли typedef и #define одинаковыми в c?
Ответ 1
Нет.
#define
- токен препроцессора: сам компилятор его никогда не увидит. typedef
- это токен компилятора: препроцессор не заботится об этом.
Вы можете использовать тот или иной инструмент для достижения такого же эффекта, но лучше использовать его для своих нужд
#define MY_TYPE int
typedef int My_Type;
Когда вещи становятся "волосатыми", использование правильного инструмента делает его правильным.
#define FX_TYPE void (*)(int)
typedef void (*stdfx)(int);
void fx_typ(stdfx fx); /* ok */
void fx_def(FX_TYPE fx); /* error */
Ответ 2
typedef
подчиняется правилам области видимости точно так же, как переменные, тогда как define
остается в силе до конца модуля компиляции (или до соответствующего undef
).
Кроме того, некоторые вещи могут быть выполнены с помощью typedef
что невозможно сделать с помощью define
.
Например:
typedef int* int_p1;
int_p1 a, b, c; // a, b, c are all int pointers
#define int_p2 int*
int_p2 a, b, c; // only the first is a pointer, because int_p2
// is replaced with int*, producing: int* a, b, c
// which should be read as: int *a, b, c
typedef int a10[10];
a10 a, b, c; // create three 10-int arrays
typedef int (*func_p) (int);
func_p fp; // func_p is a pointer to a function that
// takes an int and returns an int
Ответ 3
Нет, они не то же самое. Например:
#define INTPTR int*
...
INTPTR a, b;
После предварительной обработки эта строка расширяется до
int* a, b;
Надеюсь, вы увидите проблему; только a
будет иметь тип int *
; b
будет объявлен простой int
(поскольку *
связан с объявлением, а не с спецификатором типа).
Контрастируйте это с помощью
typedef int *INTPTR;
...
INTPTR a, b;
В этом случае оба a
и b
будут иметь тип int *
.
Существуют целые классы typedefs, которые нельзя эмулировать с помощью макроса препроцессора, например указатели на функции или массивы:
typedef int (*CALLBACK)(void);
typedef int *(*(*OBNOXIOUSFUNC)(void))[20];
...
CALLBACK aCallbackFunc; // aCallbackFunc is a pointer to a function
// returning int
OBNOXIOUSFUNC anObnoxiousFunc; // anObnoxiousFunc is a pointer to a function
// returning a pointer to a 20-element array
// of pointers to int
Попробуйте сделать это с помощью макроса препроцессора.
Ответ 4
#define определяет макросы.
typedef определяет типы.
Теперь, сказав это, вот несколько отличий:
С #define вы можете определить константы, которые можно использовать во время компиляции. Константы могут использоваться с #ifdef, чтобы проверить, как скомпилирован код, и специализировать определенный код в соответствии с параметрами компиляции.
Вы также можете использовать #define, чтобы объявить миниатюру find-and-replace Макрофункции.
typedef можно использовать для создания псевдонимов для типов (что вы, вероятно, могли бы сделать с #define), но это безопаснее из-за поиска и замены характер констант #define.
Кроме того, вы можете использовать
Ответ 5
Макросы препроцессора ( "#define
's" ) являются лексическим инструментом замены a la "поиск и замена". Они полностью агностичны для языка программирования и не понимают, что вы пытаетесь сделать. Вы можете думать о них как о прославленном механизме копирования/пасты - иногда это полезно, но вы должны использовать его с осторожностью.
Typedefs - это функция языка C, которая позволяет создавать псевдонимы для типов. Это чрезвычайно полезно для чтения сложных и сложных команд сложных типов (например, структур и указателей функций) (в С++ существуют ситуации, когда вы должны ввести тип).
Для (3): вы всегда должны предпочесть языковые функции поверх макросов препроцессора, когда это возможно! Поэтому всегда используйте typedefs для типов и постоянные значения для констант. Таким образом, компилятор может реально взаимодействовать с вами. Помните, что компилятор - ваш друг, поэтому вы должны рассказать об этом как можно больше. Макросы препроцессора выполняют прямую противоположность, скрывая семантику от компилятора.
Ответ 6
Они очень разные, хотя они часто используются для реализации пользовательских типов данных (что я и предполагаю, что этот вопрос есть).
Как упоминалось выше, #define
обрабатывается предварительным процессором (например, операция вырезания и вставки), прежде чем компилятор увидит код, а typedef
интерпретируется компилятором.
Одно из основных отличий (по крайней мере, когда дело доходит до определения типов данных) заключается в том, что typedef
позволяет более точно проверять тип. Например,
#define defType int
typedef int tdType
defType x;
tdType y;
Здесь компилятор видит переменную x как int, но переменную y как тип данных, называемую tdType, которая имеет тот же размер, что и int. Если вы написали функцию, которая приняла параметр типа defType, вызывающий может передать нормальный int, и компилятор не узнает разницу. Если вместо этого вместо параметра tdType была выбрана функция, компилятор обеспечил бы, чтобы во время вызова функции использовалась переменная соответствующего типа.
Кроме того, некоторые отладчики имеют возможность обрабатывать typedef
s, что может быть гораздо более полезным, чем использование всех настраиваемых типов в качестве базовых примитивных типов (как это было бы, если бы вместо #define
).
Ответ 7
Нет.
typedef - это ключевое слово C, которое создает псевдоним для типа.
#define - это предпроцессорная инструкция, которая создает событие замены текста перед компиляцией. Когда компилятор попадает в код, исходного слова "#defined" больше не существует. #define в основном используется для макросов и глобальных констант.
Ответ 8
AFAIK, No.
'typedef' помогает вам настроить псевдоним существующего типа данных. Напр. typedef char chr;
#define - это директива препроцессора, используемая для определения макросов или общих подстановок шаблонов. Напр. #define MAX 100, заменяет все вхождения MAX со 100
Ответ 9
Как сказано выше, они не совпадают. Большинство ответов показывают, что typedef
будет более выгодным, чем #define
.
Но позвольте мне добавить плюс #define
: когда ваш код чрезвычайно велик, разбросанный по многим файлам, лучше использовать #define
; это помогает в удобочитаемости - вы можете просто предварительно обработать весь код, чтобы увидеть фактическое определение типа переменной в месте самого объявления.