Storage Classes and Scope

 

The term storage class refers to the manner in which memory is allocated by the compiler in the case of variables and to the scope of a particular function or method definition. Storage classes are auto, static, extern, and register.A storage class can be omitted in a declaration, and a default storage class will be assigned, as discussed next.

The term scope refers to the extent of the meaning of a particular identifier within a program.An identifier defined outside any function, method, or statement block (herein referred to as a BLOCK) can be referenced anywhere subsequent in the file. Identifiers defined within a BLOCK are local to that BLOCK and can locally redefine an identifierdefined outside it. Label names are known throughout the BLOCK, as are formal parameter names. Labels, instance variables, structure and structure member names, union and union member names, and enumerated type names do not have to be distinct from each other or from variable, function, or method names. However, enumeration identifiers do have to be distinct from variable names and from other enumeration identifiers defined within the same scope. Class names have global scope and must be distinct from other variables and type names with the same scope.

Functions

If a storage class is specified when a function is defined, it must be either static or extern. Functions that are declared static can be referenced only from within the same file that contains the function. Functions specified as extern (or that have no class specified) can be called by functions or methods from other files.

Variables

Table B.5 summarizes the various storage classes that can be used in declaring variables as well as their scopes and methods of initialization.

Table B.5 Variables: Summary of Storage Classes, Scope, and Initialization.


If storage
class is
And variable
is declared
Then it can be referenced
And be initialized withComments
static




Outside any BLOCKAnywhere within the file
Constant expression onlyVariables are initialized only once at the start of program execution; values are retained through BLOCKS; the default value is 0
 Inside a
Block
 Within the Block
extern





Outside any BLOCKAnywhere within the fileConstant expression onlyVariable must be declared in at least one place without the extern keyword, or in one place using the keyword extern and
assigned an initial value
 Inside a BLOCKWithin the BLOCK
auto

Inside a BLOCKWithin the BLOCK Any valid expressionVariable is initialized each time the BLOCK is entered; no default value
registerInside a
BLOCK
Within the BLOCKAny valid expressionAssignment register not guaranteed; varying
restrictions on types of variables that can be
declared; cannot take the address of a
register variable; initialized each time
BLOCK is entered; no default value
omitted





Outside any BLOCKAnywhere within the file or by other files that contain appropriate declarationsConstant
expressions
only
This declaration can appear in only one
place; the variable is initialized at the start
of program execution; the default value is 0;
it defaults to auto
 Inside a BLOCK(See auto)(See auto)

 

Instance Variables

Instance variables can be accessed by any instance method defined for the class, either in the interface section that explicitly defines the variable or in categories created for the class. Inherited instance variables can also be accessed directly without any special declarations. Class methods do not have access to instance variables.

The special directives @private, @protected, and @public can be used to control the scope of an instance variable. After these directives appear, they remain in effect until the closing curly brace ending the declaration of the instance variables is encountered or until another of the three listed directives is used. For example, the following begins an interface declaration for a class called Point containing four instance variables:

@interface Point: NSObject
{
@private
    int internalID;
@protected
    float x;
    float y;
@public
    BOOL valid;
}

The internalID variable is private, the x and y variables are protected (the default), and the valid variable is public.

These directives are summarized in Table B.6.
Table B.6 Scope of Instance Variables


If variable is declared after this directive...
...then it can be referenced...
Comments
@protected



By instance methods in the class, instance methods in subclasses, and instance methods in category extensions to the classThis is the default.
@privateBy instance methods in the class and instance methods in any category extensions to the class, but not by any subclassesThis restricts access to the class itself.
@public
By instance methods in the class, instance methods in subclasses, and instance methods in category extensions to the class; it can also be accessed from other functions or methods by applying the structure pointer indirection operator (->) to an instance of the class followed by the
name of the instance variable (as in myFract->numerator)
This should not be used unless necessary; it defeats the notion of data encapsulation.