В разделе 7.1 стандарта C ++ упоминается extern как спецификатор класса хранения.
N3126 - «Спецификатор extern может применяться только к именам переменных и функций. Спецификатор extern не может использоваться в объявлении членов класса или параметров функции. Для связывания имени, объявленного со спецификатором extern, см. 3.5. [ Примечание. Ключевое слово extern также может использоваться в явных экземплярах и спецификациях связывания, но оно не является спецификатором класса хранилища в таких контекстах. - конец примечания]
Я понимаю это ключевое слово и его использование в контексте «спецификации связывания», но я не могу понять использование «extern» в качестве спецификатора хранилища.
- Разве все внешние имена не имеют статической продолжительности хранения?
- Если ответ на 1 - «да», то почему эта избыточность? C Совместимость?
3 ответа
extern
- это спецификатор класса хранения . Это просто факт грамматики языка. extern
оказывает ряд эффектов на семантику программы в зависимости от того, где она используется. Это не везде одинаково. Он влияет на продолжительность хранения и связь объектов, а также помогает определить, являются ли некоторые объявления также определениями или нет.
Например.:
int a; // Ex1
extern int b; // Ex2
Например, если Ex1
и Ex2
находятся в глобальной области видимости, то они оба будут ссылаться на объекты со статической продолжительностью хранения и внешней связью. Однако в C ++ первое будет определением (предварительное определение в C), а второе - нет. В этом примере extern
не изменил продолжительность хранения или привязку объявленного объекта.
Если Ex1
и Ex2
встречаются в теле функции, то a
будет ссылаться на объект с автоматической продолжительностью хранения и без связи, но b
будет ссылаться на объект с внешней связью и статическая продолжительность хранения. В этом примере extern
повлиял на значение объявления как в связи, так и в продолжительности хранения, а также в том, является ли это определением.
Наконец, в C ++ приведен пример, в котором единственным эффектом extern
является изменение связи с внутренней на внешнюю.
const int c = 5; // static storage duration, internal linkage
extern const int d = 10; // static storage duration, external linkage
Это не действительно спецификатор хранилища как таковой. Он стоит перед именем переменной, как и другие спецификаторы хранилища, но все, что он делает, - это закрывает компилятор и сообщает компоновщику, что у него еще есть работа.
static
, auto
, register
) определяют, в какой памяти будет храниться переменная. Другие классы хранения (const
, volatile
) влияют на то, как компилятор генерирует код для доступа к ним. extern
тоже не умеет.
const
и volatile
не являются спецификаторами класса хранения, они являются квалификаторами типа. Поскольку вам разрешен только один спецификатор класса хранения в объявлении, если const
где один, то (например) static const int x = 5;
будет незаконным. Насколько мне известно, это верно как для C, так и для C ++.
Ключевое слово Extern сообщает компилятору, что существует внешняя переменная (или функция), даже если компилятор не может найти ее в текущем компилируемом файле. Вынуждает внешнюю связь.
Похожие вопросы
Связанные вопросы
Новые вопросы
c++
C++ — это язык программирования общего назначения. Изначально он разрабатывался как расширение C и имел аналогичный синтаксис, но теперь это совершенно другой язык. Используйте этот тег для вопросов о коде, который будет скомпилирован с помощью компилятора C++. Используйте тег версии для вопросов, связанных с конкретной стандартной версией [C++11], [C++14], [C++17], [C++20] или [C++23]. и т.д.
typedef
в набор спецификаторов класса хранения -typedef
не имеет ничего общего с хранилищем или связью ...