2010-05-26 4 views
8

Если название не было ясно, я попытаюсь пояснить, что я спрашиваю:Access значение переменной, используя строку, представляющую имя переменной в C++

Представьте я переменную счетчик, я знаю, что могу видеть его текущее значение, делая что-то вроде:

std::cout << counter << std::endl; 

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

Кто-нибудь знает, как я могу получить значение переменной, используя его имя, например:

std::cout << valueOf("counter") << std::endl; 

Я чувствую, будучи в состоянии сделать это может сделать отладку крупных комплексных проектов проще.

Заранее благодарим за ваше время.


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

+0

Эта строка 'counter' известна в * компиляции-времени *? – kennytm

+6

это называется «отладчик» - он позволяет вам проверять значения переменных во время выполнения, среди других полезных функций: – Drakosha

+0

Я хорошо знаю отладчики и отладку, другие ответы, которые я задавал об отражении, - это термин, который я раньше не знал из ... –

ответ

10

Как уже упоминалось, вы ищете отражение на C++. Это не так, и this answer объясняет, почему.

0

Для этого потребуется что-то похожее на отражение или eval, которого нет у C++.

0

Нет, C++ не предоставляет эту возможность. Вы можете взломать что-то вместе с макросами (или другими обманами), но это, скорее всего, будет довольно уродливым.

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

+0

Это очень полезно при отладке Generic Algorithms. Когда что-то терпит неудачу в общем алгоритме, действительно помогает увидеть имя фактического типа. Часто отладчики не отображают это. –

4

Вы можете использовать ассоциативный контейнер как std :: map < std :: string, your_variable_type>, чтобы связать строку с переменной, если они все одного типа.

Если у вас есть переменная различных типов, решение существует, так как в буст :: вариант

1

C++ обращается ко всем переменным через адрес, так что нет никакого способа, чтобы просто сказать valueOf переменную (Языки, которые позволяют это, например, питон, perl имеют время выполнения, сохраняющее эту информацию)

Вы можете реализовать что-то, позволяющее использовать имя, чтобы найти значение, сохраняя значения и их имена в std :: map.

1

Ну, если вы действительно хотите сделать что-то подобное, вы можете попробовать использовать std :: map (map < string, int *>). Hovewer это ограничило бы вас одним типом переменной, если вы не вникаете в какую-то уродливую магию указателя. В любом случае это будет уродливо и поверьте мне, что вы действительно не хотите идти по этому пути. Зачем вам такая функция? Если для целей отладки используется отладчик.

3

Нет, не с C++ или его стандартной библиотекой. Конечно, вы можете взломать что-то, чтобы подражать этому поведению. C++ позволяет вам выбирать методы во время выполнения, используя полиморфизм, чтобы вы могли воспользоваться этим.В сущности, вы получите метод для вызова во время выполнения, а не переменный, а метод возвращает vlaue:

struct Value { 
    virtual ~Value(); 
    virtual std::string value() const = 0; 
}; 

struct Counter : public Value { 
    int v; 
    std::string value() const { 
     istringstream ss(v); 
     return ss.str(); 
    } 
}; 

struct Mounter : public Value { 
    double v; 
    std::string value() const { 
     istringstream ss(v); 
     return ss.str(); 
    } 
}; 

Value* get_value(); 

// ... 
cout << get_value()->value() << endl; 

В качестве альтернативы, вы можете сохранить карту с ключом по строкам, имена значения, а затем посмотреть значения с их именами.

1

Как уже говорилось, C++ не дает никакого отражения. Но вы можете использовать некоторое отображение ключевых/значений самостоятельно. Если требуется только один тип значения (например, int), вы можете использовать ассоциативный контейнер (карту) STL из коробки. Если вам нужно поддерживать несколько типов значений, я рекомендую посмотреть в библиотеку ускорений Variant.

Смежные вопросы