Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате
Форум программистов > PHP: Общие вопросы > О #ifdef в PHP.


Автор: Elfet 3.3.2010, 22:20
В своем проекте мне понадобилось собирать различные версии исходников. Причём так что бы в различных сборках помещались различные куски кода. if-else мне здесь не подходил, потому что нужно было что бы код либо точно входил, либо не входил в сборку.

Решение

Поэтому я решил использовать директивы #ifdef/#endif. Для их реализации я создал небольшую программку на C#, которая обрабатывает эти директивы. В программе нужно указать исходный файл или папку, и папку куда нужно помещать готовый результат. На наличие директив обрабатываются только php файлы, остальные просто копируются.
PHP Ifdef Collector PrintScreen

Работа программы

Программа имеет глобальный массив defines, который создаётся из третьего поля («Defines (comma separated)»). Этот массив может быть дополнен директивой «#define TEXT» в php коде.
Программа умеет обрабатывать следующие директивы: «#ifdef TEXT», «#ifndef TEXT». Первая включает код если директива определена, вторая включает если не определена. Эти директивы обязательно должны иметь закрывающие «#endif».
Так же программа умеет обрабатывать «#else» и вложенность этих директив.

Заключение

Поскольку в php символ «#» определяет комментарий, то код может быть выполнен и без вырезания этих директив.
Однако, если использовать «#ifdef — #else — #endif» с кодом выполняющим различные действия с одними и теми же данными, то нужно закомментировать одно из этих действий для его выполнения без вырезания директив примерно следующим образом:

Код

<?php
#ifdef COPY

$chat_page = new View('copy');
$chat_page->SetVars(array('copyright' => $this->Copyright()));
$this->html = $chat_page->Get();
$this->Display();

/*#else

$this->html = View('no_copy')::Call();
$this->Display();

*/#endif
?>



Скачать программу можно здесь: http://phpifdef.googlecode.com/files/Php%20Ifdef%20Collector.exe
Исходники программы тут: http://code.google.com/p/phpifdef/

P.S.
Выложил свою первую статью на хабре: http://habrahabr.ru/blogs/php/84964/.
Там она набрала много отрицательных и всего несколько положительных голосов.  smile 

Автор: nerezus 4.3.2010, 00:37
А чем не покатит if? o_O

Автор: Elfet 4.3.2010, 01:30
Тем что мне нужно собирать различные версии исходников с различным кодом. 

Автор: bars80080 4.3.2010, 02:06
Цитата(Elfet @  3.3.2010,  21:20 Найти цитируемый пост)
Там она набрала много отрицательных и всего несколько положительных голосов. 

как странно, да?


хотя какая может быть реакция, если это очередной eval?

Автор: perloid 4.3.2010, 03:04
раньше использовал стандартный препроцессор от c++ не помню как называется,  
и еще более продвинутый m4
но это все костыли, которые больше мешают и создают лишние проблемы.

а то что на C# написано так это большой минус, т.к. изза мелкой утилиты зависисость от большого рантайма.

Автор: nerezus 4.3.2010, 03:50
Цитата

Тем что мне нужно собирать различные версии исходников с различным кодом. 
 
Вы наверное не поняли. Повторю свой вопрос: чем if не угодил?

Автор: awers 4.3.2010, 08:05
Что то мне задача совершенно непонятна. Может лучше юзать svn/git и соответственно tags/branches?

Автор: skyboy 4.3.2010, 11:30
Elfet, интересная идея - простой препроцессор.
действительно, в отличие от if / else эти конструкции вполне могут находиться в любом месте кода, например, внутри определения класса:
Код

class test {
#ifdef PHP5
public static function test() {
}
#else
function test() {
}
#endif
}

куда if не впихнешь. 
в принципе, я вижу одно применение: слияние РНР4 и РНР5-версий кода в один файл.
все остальные применения, которые приходят мне в голову(переключение используемых механизмов, изменение поведения в зависимости от некоторых внешних по отношению к системе параметров) проигрывают в ясности и расширяемости использованию http://ru.wikipedia.org/wiki/%D0%A4%D0%B0%D0%B1%D1%80%D0%B8%D1%87%D0%BD%D1%8B%D0%B9_%D0%BC%D0%B5%D1%82%D0%BE%D0%B4_(%D1%88%D0%B0%D0%B1%D0%BB%D0%BE%D0%BD_%D0%BF%D1%80%D0%BE%D0%B5%D0%BA%D1%82%D0%B8%D1%80%D0%BE%D0%B2%D0%B0%D0%BD%D0%B8%D1%8F) и/или файлов конфигураций. 
да и include/require c динамически формируемыми именами("toolkit.php4.php"/"toolkit.php5.php") позволяет сделать то же. 
даже если класс/функция должна иметь разный интерфейс(наборы методов у класса, параметров функции) в зависимости от определенных условий(что уж попахивает ошибкой проектирования) - require решает.
а у препроцессинга как средства определения поведения кода есть крупный недостаток: нечитабельность. тем более, что отладка будет производиться на уже обработанной препроцессором частной версией кода, а писать код надо в "полной" версии. и получается - пишем в одном месте, отлаживаем в другом. не говоря уже о том, что подобные конструкции как абсолютно не типичные для языка, в любом редакторе предстанут обычными комментариями, что ничуть не упростит написание кода.

Автор: nerezus 4.3.2010, 13:04
Цитата

в принципе, я вижу одно применение: слияние РНР4 и РНР5-версий кода в один файл.
 Ну это было актуально лет 5 назад все же, сейчас пхп4 не поддерживается.
Так что имхо бесполезная вещь-костыль для не фанатов проектирования.

Автор: Elfet 4.3.2010, 14:36
skyboy, я вначале использовал разные файлы и подключал разные классы унаследованные от одного интерфейса. 

Директивы #ifdef я не предлагаю как панацея от всего, всего лишь ещё один способ сделать проще что-то.

Добавлено через 3 минуты и 13 секунд
А использую я это в своём проекте чата, так как я делаю две версии бесплатную и платную. Можно конечно было бы использовать ветку в svn, как предложил 
awers, но мне пока больше нравится мой вариант. 

Автор: IZ@TOP 4.3.2010, 15:13
А для чего это нужно? Можно хотя бы одну живую рабочую версию?

Добавлено через 3 минуты и 10 секунд
Цитата(Elfet @  4.3.2010,  15:36 Найти цитируемый пост)
А использую я это в своём проекте чата, так как я делаю две версии бесплатную и платную. Можно конечно было бы использовать ветку в svn, как предложил 
awers, но мне пока больше нравится мой вариант.  

Все равно стырят. А для того, что бы сделать платную и бесплатную, не обязательно добавлять такой изврат, достаточно изучить несколько паттернов и делать сборки для разных версий, совместно с svn это было бы еще проще.

Автор: Elfet 4.3.2010, 23:36
Цитата(IZ@TOP @  4.3.2010,  16:13 Найти цитируемый пост)
А для чего это нужно? Можно хотя бы одну живую рабочую версию?

Я в своём чате это использую. 


Цитата(IZ@TOP @  4.3.2010,  16:13 Найти цитируемый пост)
достаточно изучить несколько паттернов и делать сборки для разных версий, совместно с svn это было бы еще проще. 

Иногда нужно заменить всего несколько строк в коде и прикручивать какие-то паттерны смысла нету, тут я и использую #ifdef

В С++ очень широко используются эти препроцессоры, так почему бы их и в php не использовать? 

P.S. Паттерны это конечно же хорошо, но как-то последнее время их предлагают использовать практически для всего, как и ООП, что не всегда является наилучшим вариантом.  

Автор: IZ@TOP 5.3.2010, 11:04
Цитата(Elfet @  5.3.2010,  00:36 Найти цитируемый пост)
В С++ очень широко используются эти препроцессоры, так почему бы их и в php не использовать? 

C++ язык высокого уровня, которые применяется для решения задач в разных областях. PHP же, язык скриптовый, специализированный под веб, где существуют стандартные решения для коммерции. Я уже не говорю о том, что ты себе этим прекомпилируемым PHP кучу проблем доставишь при отладке.

Цитата(Elfet @  5.3.2010,  00:36 Найти цитируемый пост)
P.S. Паттерны это конечно же хорошо, но как-то последнее время их предлагают использовать практически для всего, как и ООП, что не всегда является наилучшим вариантом.  

А почему не использовать, если для решения большинства задач уже есть готовые схемы? Изобретаем велосипеды, а потом их постоянно переделываем.

Автор: Elfet 5.3.2010, 12:27
Цитата(IZ@TOP @  5.3.2010,  12:04 Найти цитируемый пост)
А почему не использовать, если для решения большинства задач уже есть готовые схемы? Изобретаем велосипеды, а потом их постоянно переделываем. 

Да, для решения части задач можно использовать и паттерны. Но это не всегда лучший вариант. 

Автор: MoLeX 5.3.2010, 13:38
Цитата(Elfet @  4.3.2010,  14:36 Найти цитируемый пост)
но мне пока больше нравится мой вариант.  

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



Elfet, а смысл этим хвастаться показывать на форуме? Для 99,9% это ненужная утилита... 

Автор: IZ@TOP 5.3.2010, 14:37
Цитата(Elfet @  5.3.2010,  13:27 Найти цитируемый пост)
Да, для решения части задач можно использовать и паттерны. Но это не всегда лучший вариант.  

Просто вы не умеете их готовить (С) кто-то
Это все равно, что сказать "Да, для некоторых авто можно использовать и колеса... но это не всегда лучший вариант". Без сомнения, антигравитационная система лучше, но кто же ее реализует?

Автор: Elfet 5.3.2010, 15:16
MoLeX, 99% пользоваться не будут. А 1% будет - для них и выложил. Жалко что ли? smile


IZ@TOP, иногда вместо колёс ставят гусеницы =)) 

Автор: LeoK 5.3.2010, 15:16
Я так понимаю вы решили сделать препроцессор для пхп?

Похвально конечно, но не стоит забывать что мы интерпретатор smile

Powered by Invision Power Board (http://www.invisionboard.com)
© Invision Power Services (http://www.invisionpower.com)