logo

C Препроцесори

Препроцесори - це програми, які обробляють вихідний код перед компіляцією. Між написанням програми та її виконанням на С є кілька кроків. Давайте подивимося на ці кроки, перш ніж ми почнемо вивчати препроцесори.

препроцесори в c



Ви можете побачити проміжні кроки на схемі вище. Вихідний код, написаний програмістами, спочатку зберігається у файлі, нехай буде назва програма.c . Потім цей файл обробляється препроцесорами, і генерується розширений файл вихідного коду під назвою program.i. Цей розгорнутий файл компілюється компілятором і створюється файл об’єктного коду під назвою program.obj. Нарешті, компонувальник зв’язує цей файл об’єктного коду з об’єктним кодом функцій бібліотеки, щоб створити виконуваний файл program.exe.

Директиви препроцесора в C

Програми препроцесора надають директиви препроцесора, які вказують компілятору попередньо обробити вихідний код перед компіляцією. Усі ці директиви препроцесора починаються з символу «#» (решетка). Символ «#» вказує на те, що будь-який оператор, який починається з «#», буде передано програмі препроцесора для виконання. Ми можемо розмістити ці директиви препроцесора будь-де в нашій програмі.

Приклади деяких директив препроцесора: #включати , #визначити , #ifndef, тощо



Примітка Пам'ятайте, що # символ лише надає шлях до препроцесора, а така команда, як include, обробляється програмою препроцесора. Наприклад, #include включить код або вміст зазначеного файлу у вашу програму.

Список директив препроцесора в C

У наступній таблиці перераховані всі директиви препроцесора в C:

Директиви препроцесора

опис



#визначити

Використовується для визначення макросу

#undef

Використовується для скасування визначення макросу

#включати

Використовується для включення файлу у вихідний код програми

#ifdef

Використовується для включення частини коду, якщо певний макрос визначено за допомогою #define

#ifndef

Використовується для включення частини коду, якщо певний макрос не визначено #define

#якщо

Перевірити вказану умову

#інше

Альтернативний код, який виконується, коли #if не вдається

#endif

Використовується для позначення кінця #if, #ifdef і #ifndef

Ці препроцесори можна класифікувати на основі типу функції, яку вони виконують.

команда arp-a

Типи препроцесорів C

Існує 4 основних типи директив препроцесора:

  1. Макроси
  2. Включення файлу
  3. Умовна компіляція
  4. Інші директиви

Давайте тепер докладніше дізнаємося про кожну з цих директив.

1. Макроси

У C макроси — це фрагменти коду в програмі, яким присвоєно певне ім’я. Кожного разу, коли компілятор зустрічає це ім’я, компілятор замінює ім’я фактичним фрагментом коду. The '#define' Директива використовується для визначення макросу.

Синтаксис визначення макросу

  #define     token     value>

де після попередньої обробки, жетон буде розширено до його значення в програмі.

Приклад макросу

C




// C Program to illustrate the macro> #include> // macro definition> #define LIMIT 5> int> main()> {> >for> (>int> i = 0; i printf('%d ', i); } return 0; }>

>

успадкування в java
>

Вихід

0 1 2 3 4>

У наведеній вище програмі, коли компілятор виконує слово LIMIT, він замінює його на 5. Слово «ОБМЕЖЕННЯ» у визначенні макросу називається шаблоном макросу і «5» — розширення макросу.

Примітка У кінці визначення макросу немає крапки з комою (;). Визначення макросів не потребують крапки з комою в кінці.

Є й такі Попередньо визначені макроси в C які корисні для надання різноманітних функцій нашій програмі.

Макроси з аргументами

Ми також можемо передавати аргументи макросам. Макроси, визначені аргументами, працюють подібно до функцій.

приклад

  #define   foo(  a, b  )   a + b  #define func(r) r * r>

Давайте зрозуміємо це за допомогою програми:

C




// C Program to illustrate function like macros> #include> // macro with parameter> #define AREA(l, b) (l * b)> int> main()> {> >int> l1 = 10, l2 = 5, area;> >area = AREA(l1, l2);> >printf>(>'Area of rectangle is: %d'>, area);> >return> 0;> }>

>

>

Вихід

if else if java
Area of rectangle is: 50>

З наведеної вище програми ми бачимо, що коли компілятор знаходить AREA(l, b) у програмі, він замінює його оператором (l*b). Не тільки це, але й значення, передані до шаблону макросу AREA(l, b), також буде замінено в операторі (l*b). Тому ПЛОЩА(10, 5) дорівнюватиме 10*5.

2. Включення файлу

Цей тип директиви препроцесора повідомляє компілятору включити файл у вихідний код програми. The Директива препроцесора #include використовується для включення файлів заголовків у програму C.

Існує два типи файлів, які користувач може включити в програму:

Стандартні файли заголовків

Стандартні файли заголовків містять визначення попередньо визначених функцій, таких як printf(), scanf(), і т. д. Ці файли повинні бути включені для роботи з цими функціями. Різні функції оголошуються в різних файлах заголовків.
Наприклад, стандартні функції вводу/виводу знаходяться у файлі «iostream», тоді як функції, які виконують рядкові операції, знаходяться у файлі «рядок».

Синтаксис

  #include   <  file_name>>

де ім'я_файлу це ім'я файлу заголовка, який буде включено. The «дужки». скажіть компілятору шукати файл у s стандартний каталог.

Визначені користувачем файли заголовків

Коли програма стає дуже великою, доцільно розділити її на менші файли та включати їх у разі потреби. Ці типи файлів є файлами заголовків, визначеними користувачем.

Синтаксис

  #include   '  filename  '>

The подвійні лапки ( ) скажіть компілятору шукати файл заголовка в каталог вихідного файлу.

3. Умовна компіляція

Умовна компіляція в директивах C це тип директиви, який допомагає скомпілювати певну частину програми або пропустити компіляцію певної частини програми на основі певних умов. Існують такі директиви препроцесора, які використовуються для вставки умовного коду:

  1. Директива #if
  2. Директива #ifdef
  3. Директива #ifndef
  4. Директива #else
  5. Директива #elif
  6. Директива #endif

#endif Директива використовується для закриття початкових директив #if, #ifdef і #ifndef, що означає, що попередню обробку цих директив завершено.

Синтаксис

  #ifdef     macro_name   // Code to be executed if macro_name is defined #  ifndef     macro_name   // Code to be executed if macro_name is not defined   #if    constant_expr   // Code to be executed if constant_expression is true   #elif     another_constant_expr   // Code to be excuted if another_constant_expression is true   #else   // Code to be excuted if none of the above conditions are true   #endif>

Якщо макрос із назвою « ім'я_макросу ‘ визначено, тоді блок операторів виконуватиметься нормально, але якщо він не визначений, компілятор просто пропустить цей блок операторів.

приклад

Наведений нижче приклад демонструє використання директив препроцесора #include #if, #elif, #else і #endif.

C




//program to demonstrates the use of #if, #elif, #else,> // and #endif preprocessor directives.> #include> // defining PI> #define PI 3.14159> int> main()> {> > #ifdef PI> >printf>(>'PI is defined '>);> > #elif defined(SQUARE)> >printf>(>'Square is defined '>);> #else> >#error 'Neither PI nor SQUARE is defined'> #endif> > #ifndef SQUARE> >printf>(>'Square is not defined'>);> #else> >cout <<>'Square is defined'> << endl;> #endif> >return> 0;> }>

>

>

Вихід

PI is defined Square is not defined>

4. Інші директиви

Окрім наведених вище директив, є ще дві директиви, які зазвичай не використовуються. Це:

  1. Директива #undef
  2. Директива #pragma

1. Директива #undef

Директива #undef використовується для скасування визначення існуючого макросу. Ця директива працює як:

#undef LIMIT>

Використання цього оператора скасує визначення існуючого макросу LIMIT. Після цього оператора кожен оператор #ifdef LIMIT оцінюватиметься як false.

приклад

Наведений нижче приклад демонструє роботу директиви #undef.

C




#include> // defining MIN_VALUE> #define MIN_VALUE 10> int> main() {> >// Undefining and redefining MIN_VALUE> printf>(>'Min value is: %d '>,MIN_VALUE);> > //undefining max value> #undef MIN_VALUE> > // again redefining MIN_VALUE> #define MIN_VALUE 20> >printf>(>'Min value after undef and again redefining it: %d '>, MIN_VALUE);> >return> 0;> }>

>

>

Вихід

період ключ
Min value is: 10 Min value after undef and again redefining it: 20>

2. Директива #pragma

Ця директива є спеціальною і використовується для ввімкнення або вимкнення деяких функцій. Ці типи директив є специфічними для компілятора, тобто вони відрізняються від компілятора до компілятора.

Синтаксис

#pragma   directive>

Деякі з директив #pragma обговорюються нижче:

  1. #pragma запуск: Ці директиви допомагають нам визначити функції, які необхідно виконати перед запуском програми (до того, як керування перейде до main()).
  2. #pragma вихід : Ці директиви допомагають нам указати функції, які необхідно запускати безпосередньо перед виходом з програми (безпосередньо перед поверненням керування з main()).

Наведена нижче програма не працюватиме з компіляторами GCC.

приклад

Програма нижче проілюструйте використання #pragma exit і pragma startup

C




// C program to illustrate the #pragma exit and pragma> // startup> #include> void> func1();> void> func2();> // specifying funct1 to execute at start> #pragma startup func1> // specifying funct2 to execute before end> #pragma exit func2> void> func1() {>printf>(>'Inside func1() '>); }> void> func2() {>printf>(>'Inside func2() '>); }> // driver code> int> main()> {> >void> func1();> >void> func2();> >printf>(>'Inside main() '>);> >return> 0;> }>

>

>

Очікуваний результат

Inside func1() Inside main() Inside func2()>

Наведений вище код створюватиме вихідні дані, як наведено нижче, якщо працювати на компіляторах GCC:

Inside main()c>

Це відбувається тому, що GCC не підтримує запуск або вихід #pragma. Однак ви можете використовувати наведений нижче код для очікуваного результату на компіляторах GCC.

C




#include> void> func1();> void> func2();> void> __attribute__((constructor)) func1();> void> __attribute__((destructor)) func2();> void> func1()> {> >printf>(>'Inside func1() '>);> }> void> func2()> {> >printf>(>'Inside func2() '>);> }> int> main()> {> >printf>(>'Inside main() '>);> >return> 0;> }>

java, якщо інше

>

>

Вихід

Inside func1() Inside main() Inside func2()>

У наведеній вище програмі ми використали деякі специфічний синтаксис так що одна з функцій виконується перед основною функцією, а інша – після основної функції.

Директива #pragma warn

Ця директива використовується, щоб приховати попередження, яке відображається під час компіляції. Ми можемо приховати попередження, як показано нижче:

  • #pragma попередження -rvl : Ця директива приховує ті попередження, які викликаються, коли функція, яка має повертати значення, не повертає значення.
  • #pragma попередження -пар : Ця директива приховує ті попередження, які виникають, коли функція не використовує передані їй параметри.
  • #pragma попередження -rch : Ця директива приховує ті попередження, які виникають, коли код недоступний. Наприклад, будь-який код, написаний після повернення оператор у функції недосяжний.

Якщо вам подобається techcodeview.com і ви хочете зробити внесок, ви також можете написати статтю за допомогою . Перегляньте свою статтю на головній сторінці techcodeview.com і допоможіть іншим гікам. Будь ласка, пишіть коментарі, якщо ви знайшли щось невірне або якщо ви хочете поділитися додатковою інформацією про тему, розглянуту вище.