C++ присваивает const переменной окружения или значению по умолчанию

Для приложения, которое использует несколько переменных среды, существует ли какое-то соглашение или "наилучшая практика", когда дело доходит до захвата переменных среды и помещения их в структуру или набор const"S? Очевидно, я хочу вернуться к значению по умолчанию для каждой переменной среды. Прямо сейчас использование следующего кажется очень грязным способом сделать это:

char* x;
const SOME_VARIABLE;
if (NULL == (x = getenv("SOME_VARIABLE")))
    SOME_VARIABLE = 5; // default value
else
    SOME_VARIABLE = x;

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

Какие-нибудь мысли?

3 ответа

Решение

Как насчет:

std::string GetEnvironmentVariableOrDefault(const std::string& variable_name, 
                                            const std::string& default_value)
{
    const char* value = getenv(variable_name.c_str());
    return value ? value : default_value;
}

Используется в качестве:

const std::string some_variable = GetEnvironmentVariableOrDefault("SOME_VARIABLE", "5");

Я обычно делаю это с классом, который загружает параметры конфигурации (из среды или из файла конфигурации). Я запускаю один глобальный экземпляр этого при запуске. Настройки программы - это метод или свойство объекта класса конфигурации. Это просто, и когда вы пишете код, становится достаточно ясно, что вы намеревались:

if ( configuration.ExitOnFailure && IsError() )
   exit();

James McNellis дал отличный ответ, но вот альтернативное мнение:

Я думаю getenv() возвращает значение переменной окружения во время запуска программы. Если переменная окружения изменяется после запуска программы, getenv() все равно вернет старое значение. Исходя из этого, альтернативный подход может заключаться в том, чтобы иметь класс для захвата всех необходимых переменных среды в качестве атрибутов. Класс заполняется в начале программы и предоставляет только методы доступа (соответствующие требованиям const). Таким образом, getenv() вызывается ровно один раз для каждой переменной среды. С другой стороны, класс занимает немного места.

В альтернативном подходе, который не использует пространство, getenv() вызывается всякий раз, когда требуется значение любой переменной среды. Дело не в том, что getenv() вызов дорогой (на самом деле я не знаю), но он несет ложное предположение программисту, что может быть возвращено последнее значение.

Также наличие класса может быть полезно для абстрагирования, если есть какая-либо зависимость в использовании переменных окружения, например

if $OS = "SunOs" 
then 
    GCC="/bin/gcc" 
else 
    GCC="/usr/bin/gcc" 

(this is just an example though)

Теперь функция, которая не заботится о $OS но нужно только $GCCМожно просто сослаться на envClass->get("GCC");

Просто мысль.

Другие вопросы по тегам