Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Scope of nested function declaration in C++

namespace X {
    void f();
}

void X::f() {
    void g();
    g();
}

Have I declared ::g, or X::g?

clang 3.5 will compile and link this if I add a definition of X::g:

namespace X {
    void f();
}

void X::f() {
    void g();
    g();
}

void X::g() { }

gcc 4.9.1 rejects the definition with the message:

error: ‘void X::g()’ should have been declared inside ‘X’

but if I define g in the global namespace instead, gcc seems to change it's mind and complain about the opposite:

Undefined symbols for architecture x86_64:
  "X::g()", referenced from:
      X::f()     in ccABCDEF.o

Because it is also illegal to declare void ::g() inside of f, it seems that it isn't possible to have a function-scope forward declaration of global function in a namespace function. Am I missing something? What exactly are the scoping rules here?

g++ (GCC) 4.9.1; Apple LLVM version 6.0 (clang-600.0.54) (based on LLVM 3.5svn)

like image 962
0x5f3759df Avatar asked Oct 28 '14 18:10

0x5f3759df


People also ask

What will be the scope for variables inside a nested function?

The scope of a variable is the range of functions that have direct access to the variable to set, modify, or acquire its value. When you define a local (i.e., nonglobal) variable within a function, its scope is normally restricted to that function alone.

What is nested functions in C?

A nested function is a function defined inside another function. Nested functions are supported as an extension in GNU C, but are not supported by GNU C++. The nested function's name is local to the block where it is defined.

Is nested function allowed in C?

C does not enable nested functions because we cannot define a function within another function in C. It is possible to declare a function within a function, but this is not a nested function.

What is nesting of function in C with example?

A nested function is a function defined inside the definition of another function. It can be defined wherever a variable declaration is permitted, which allows nested functions within nested functions. Within the containing function, the nested function can be declared prior to being defined by using the auto keyword.


1 Answers

Function declarations at block scope have linkage. [basic.link]/6:

The name of a function declared in block scope and [..] have linkage.

But such block scope declarations with linkage do not introduce any names into enclosing namespaces. [basic.link]/7:

When a block scope declaration of an entity with linkage is not found to refer to some other declaration, then that entity is a member of the innermost enclosing namespace. However such a declaration does not introduce the member name in its namespace scope.

You have therefore neither declared ::g nor X::g. Defining it via

void X::g() {}

is ill-formed.

like image 87
Columbo Avatar answered Oct 26 '22 16:10

Columbo