Подтвердить что ты не робот

Вопросы об управлении именами в С++

Я пытаюсь изучить и понять манипулирование именами на С++. Вот несколько вопросов:

(1) Из devx

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

Существуют ли другие примеры, использующие управление именами, помимо перегрузок функций и глобальных имен и переменных с одним и тем же именем?

(2) Из Wiki

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

Я не совсем понимаю, почему манипуляция имени применяется только к случаям, когда идентификаторы принадлежат различным пространствам имен, поскольку функции перегрузки могут находиться в одном пространстве имен, а одноименные глобальные и локальные переменные могут также находиться в одном и том же пространстве, Как это понимать?

Имеются ли переменные с одинаковым именем, но в разных областях, также с помощью mangling?

(3) Имеет ли C название mangling? Если это не так, как это может быть связано с тем случаем, когда одни глобальные и локальные переменные имеют одинаковое имя? C не имеет функций перегрузки, правильно?

Спасибо и приветствую!

4b9b3361

Ответ 1

C не обрабатывает имя, хотя он предварительно подменяет подчеркивание на имена функций, поэтому printf(3) на самом деле _printf в объекте libc.

В С++ история отличается. История этого состоит в том, что первоначально Sroustrup создал "C с классами" или cfront, компилятор, который переведет ранний С++ на C. Затем отдохните инструментов - компилятор и компоновщик C мы бы использовали для создания объектного кода. Это означало, что имена С++ должны были быть переведены на C-имена каким-то образом. Это именно то, что делает name mangling. Он предоставляет уникальное имя для каждого члена класса и функции глобального пространства имен и переменных, поэтому имена имен имен и классов (для разрешения) и типы аргументов (для перегрузки) каким-то образом включены в конечные имена компоновщика.

Это очень легко увидеть с помощью таких инструментов, как nm(1) - скомпилируйте свой источник С++ и посмотрите на сгенерированные символы. Ниже приведено описание OSX с GCC:

namespace zoom
{
    void boom( const std::string& s )
    {
        throw std::runtime_error( s );
    }
}

~$ nm a.out | grep boom
0000000100001873 T __ZN4zoom4boomERKSs

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

Edit:

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

Ответ 2

Mangling - это просто то, как компилятор поддерживает компоновщик.

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

В С++ вы можете иметь две функции с тем же именем, если они имеют разные типы параметров. Таким образом, С++ сочетает имя функции с типами в некотором роде. Таким образом, компоновщик видит в них разные имена.

Обратите внимание, что не имеет значения, как имя искажается, и на самом деле каждый компилятор делает это по-другому. Все, что имеет значение, состоит в том, что каждая функция с тем же базовым именем каким-то образом становится уникальной для компоновщика.

Теперь вы можете видеть, что добавление пространств имен и шаблонов в микс продолжает расширять принцип.

Ответ 3

Технически, он "украшает". Это звучит менее грубо, но из-за того, что CreditInterest может быть перестроено в IntCrederestit, тогда как то, что на самом деле происходит, больше похоже на [email protected], что, справедливо сказать, "украшено" более чем искаженным. Тем не менее, я называю это искалечением тоже:-), но вы найдете больше технической информации и примеров, если вы ищете "С++ name decoration".

Ответ 4

Существуют ли другие примеры, которые используют управление именами, помимо перегрузок функций и глобальных имен и глобальных имен?

С++ всегда управляет всеми символами. Это проще для компилятора. Как правило, манипуляция кодирует что-то о списке параметров или типах, поскольку они являются наиболее распространенными причинами, требующими манипулирования.

C не мешает. Scoping используется для управления доступом к локальным и глобальным переменным с тем же именем.

Ответ 5

Источник: http://sickprogrammersarea.blogspot.in/2014/03/technical-interview-questions-on-c_6.html

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

Пример:          Обычно имена участников генерируются уникально путем объединения имени элемента с именем класса, например. с учетом декларации:

class Class1
 {
        public:
            int val;
            ...
  };

val становится чем-то вроде:

  // a possible member name mangling
 val__11Class1