RDM/2 The Russian Electronic Developer Magazine  
RDM/2 Русский электронный журнал разработчика  
ДомойОт редактораПишите намОбратная связьRU/2

C Pre-Processor, но только ли для C?

Замечания к статье

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

C Pre-Processor, но только ли для C?

В процессе перевода одной программки наткнулся на некоторые интересные моменты, а именно, применение cpp отнюдь не как препроцессор для компилятора C, а как препроцессор вообще.

Была ли ситуация, когда вам нужно отделить, скажем, оформление от контента? Не знаю, как у вас, но у меня подобные вопросы возникают все время. Обычно я решаю такие проблемы используя REXX, написав простенький парсер для каждого случая. Однако, зачастую требуется стандартный набор команд. Эти команды включают в себя: if[n]def/else/endif, define, include. Плюс специфические команды, вроде текущей кодировки (sourcecodepage), необходимой кодировки (targetcodepage) и прочее.

Давайте рассмотрим ситуацию, когда необходимо сопровождать домашнюю страницу и пару ее зеркал. Причем оформление различно, равно как и требования к кодировке. Для начала примем, что все исходные файлы имеют расширение htmls (HTML Source). Итак, вот простой пример основной страницы:

----index.htmls----
#include "header.htmli"

<h1>Welcome to home of GnomoVision!</h1>

<p>GnomoVision is a program for some operations with graphics files.</p>

#include "footer.htmli"
----index.htmls----

Файлы header.htmli и footer.htmli содержат, соответственно, начало и конец страницы:

----header.htmli----
<html>
  <head>
    <title>GnomoVision Home</title>
  </head>
  <body>
----header.htmli----

----footer.htmli----
  <hr>
    <center>
      © 2002 John Doe
    </center>
  </body>
</html>
----footer.htmli----

В качестве препроцессора возьмем gnu cpp. Выполнив команду

cpp -P -C -i index.htmls -o index.html
мы получим файл index.html, который будет являть собой единое целое, состоящее из вышеперечисленных кусков. Естественно, это простейший пример, и использование cpp в такой ситуации не столь оправдано, сколь просто удобно. Но давайте рассмотрим более сложную ситуацию. Предположим, что для сервера www.host1.com нужен файл с мета-тэгом charset, а для второго (www.host2.com) этого не требуется. Внесем следующие изменения в header.htmli:
----header.htmli----
<html>
  <head>
    <title>GnomoVision Home</title>
    #ifdef HOST1
    <meta http-equiv="Content-Type" content="text/html; charset=koi8-r">
    #endif HOST1
  </head>
  <body>
----header.htmli----

При этом, для получения страниц для www.host1.com необходимо дать команду

cpp -DHOST1 -P -C -i index.htmls -o index.html
а для получения страниц для www.host2.com - ту же, что и в предыдущем примере. Давайте теперь рассмотрим случай, когда имя хоста напрямую присутствует в тексте:
----header.htmli----
#ifdef HOST1
  #define HOST 'http://www.host1.com'
#else
  #define HOST 'http://www.host2.com'
#endif
<html>
  <head>
    <title>GnomoVision Home</title>
    #if HOST1
    <meta http-equiv="Content-Type" content="text/html; charset=koi8-r">
    #endif
    <base href=HOST>
  </head>
  <body>
----header.htmli----

----index.htmls----
#include "header.htmli"

<h1>Welcome to home of GnomoVision!</h1>

<p>GnomoVision is a program for some operations with graphics files.</p>

<p>NOTE: Required <a href='/dl/file.zip'>this</a> file for Windows BMP support
#include "footer.htmli"
----index.htmls----

Обработка выполняется командой той же командой, что и в предыдущем случае.

В принципе, решение сложных задач не подвластно препроцессору, так как он имеет ряд ограничений. А именно:

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

А вот для обработки специфических команд данный препроцессор не применишь. Да и при сложных документах уже лучше применять что-то типа emxdoc, TeX (с кучей расширений) и пр., в зависимости от требований к конкретному документу.

Файлы с примером можно найти в этом архиве.

Юрий Прокушев
E-Mail: prokushev@freemail.ru
NetMail: 2:5000/106.9

---
Интересные ссылки:

---

---
Комментариев к странице: 0 | Добавить комментарий
---
Редактор: Дмитрий Бан
Оформление: Евгений Кулешов
(C) Russian Underground/2