is there a logical reason that after the keyword using namespace, we can't have a function called for example myfunction in the namespace and another function called myfunction outside the namespace (with same prototype), but we can have it for variables ( myvariable in the namespace and myvariable outside it) ?
Of course you can have a function with the same name and signature in different namespaces -- that's part of the reason namespaces exist. The only consideration is that if you want to call it you will have to qualify its name.
namespace Foo {
void func();
}
namespace Bar {
void func();
}
using namespace Foo;
using namespace Bar;
func(); // does not compile -- which func()?
Foo::func(); // ok
Bar::func(); // ok
Related
I'm doing online programming tests like leetcode, which requires only one .cpp file, so I have to place everything into one .cpp file.
And I used to write main() function ahead of any other functions, but that way I have to forward declare every function I use, which is very annoying. So I think of something like the snippet below:
namespace function;//oop,there is no such forward declaration
int main()
{
using namespace function;//compiler could not find this actually;
f1();
...
}
namespace function
{
f1(){...};
f2(){...};
...
}
But the compiler complains, since there is no forward declaration of namespaces (unlike functions), which makes the namespace invisible to the compiler.
Is there any way to forward declare a namespace? Just like
void f1();
int main()
{
f1();//ok,because there is a forward declaration
}
void f1()
{ ...}
The nearest thing to forward-declaring a namespace is to rely on the fact that they can be split up (unlike a class declaration), even into different translation units! Hence you can write
namespace funcion // [sic]
{
}
before main. Note well the braces.
If not having to forward declare functions is the most important goal, you can abuse the fact that a class also defines a namespace scope where you don't have to forward declare member functions.
Something like this:
struct program
{
int main()
{
f1();
f2();
return 0;
}
void f1(){}
void f2(){}
};
// The real main still needed here
int main()
{ return program{}.main(); }
Technically this works, but still not really recommended.
This won't solve your problem.
You can declare the namespace earlier like this:
namespace function {};
int main()
{
using namespace function;
f1();
}
namespace function
{
void f1() {}
}
but f1 is still not declared in main.
How about extracting the function declarations to a header file and including it?
somefile.h
#pragma once
namespace function {
void f1();
};
somefile.cpp
#include "somefile.h"
int main()
{
using namespace function;//compiler could not find this actually;
f1();
}
namespace function
{
void f1() {}
}
so I have to place everything into one .cpp file
Then just forget the #include and do one of the following:
a. put the declaration namespace function { void f1(); } above int main() and the definition (function body) below int main()
b. put the int main() last, so that you don't require additional declarations
I know in C++, we use :: to qualify the namespace for a variable or function, like myNamespace::a. But I notice some usages like ::myFunction(). Does it mean the function belongs to the global namespace?
If the code compiles, then yes, ::myFunction() is referencing the global declaration of myFunction.
This is most commonly used when a local definition shadows your global definition:
namespace local {
int myFunction() {}; // local namespace definition
};
int myFunction() {}; // global definition.
using namespace local;
int main() {
// myFunction(); // ambiguous two definitions of myFunction in current scope.
local::myFunction(); // uses local::myFunction();
::myFunction(); // uses global myfunction();
Yes, it means the variable, type or function following it must be available in the global namespace.
It can be used for example when something is shadowed by a local definition:
struct S {
int i;
};
void f() {
struct S {
double d;
};
S a;
::S b;
static_assert(sizeof(a) != sizeof(b), "should be different types");
}
What is the correct way to call one function from another from the same namespace when using the 'using namespace' keyword in the implementation? I get following error:
Call to 'bar' is ambiguous
when compiling this:
// Foo.h
namespace Foo
{
void bar();
void callBar();
}
// Foo.cpp
#include "Foo.h"
using namespace Foo;
void bar() {/* do something */}
void callBar() {bar();}
It appears that you are providing definitions of bar and callBar in the cpp file. In this case you should put the functions in the namespace Foo where they are declared, rather than importing that namespace with using:
#include "Foo.h"
namespace Foo {
void bar() {/* do something */}
void callBar() {bar();}
}
The using namespace directive tells the compiler that you want to call functions and refer to classes from the namespace Foo without qualifying their names explicitly; you can have multiple such directives in your file. It does not tell the compiler that the definitions that you provide below should belong to the namespace Foo, so the compiler dumps them in the top-level namespace.
The end result is that the compiler sees two bars - the Foo::bar() declared in the Foo namespace, with external definition, and ::bar() defined in your cpp file in the default namespace.
You have two bars here. one declared in namespace Foo but not defined and another declared and defined in the global namespace. Both are reachable from the call site because you are using using namespace Foo;, hence the ambiguity for the compiler.
If the definitions of the functions are for the ones in the Foo namespace then you should put them in there too.
namespace Foo {
void bar() {/* do something */}
void callBar() {bar();}
}
When defining a function signature in an anonymous namespace within a .hpp, is it valid to place the implementation of that function within the .cpp? When I do so I get an undefined reference error.
Example:
//hpp
#ifndef __BAR_HPP_
#define __BAR_HPP_
namespace foo
{
namespace
{
struct Bar
{
void func();
};
}
}
#endif
//cpp
using foo;
void Bar::func()
{
//...
}
Think of this:
namespace foo
{
struct Bar
{
void func();
};
}
void Bar::func() { /*impl...*/ }
Your code doesn't work for the same reason this code doesn't -- the definition is being provided in the wrong scope. What's needed is:
void foo::Bar::func() { /*impl...*/ }
But what do you put in place of foo:: to refer to the name of an anonymous namespace? It doesn't have one.
Bottom line: it's not possible to declare something inside of an anonymous namespace then define it elsewhere, as no mechanism exists for specifying the proper scope.
I have to use an API provided by a DLL with a header like this
namespace ALongNameToType {
class ALongNameToType {
static void Foo();
}
}
Is there a way to use ALongNameToType::ALongNameToType::Foo without having to type ALongNameToType::ALongNameToType each time? I tried using using namespace ALongNameToType but got ambiguous symbol errors in Visual Studio. Changing the namespace name or removing it gives me linker errors.
I don't know what's ambiguous, but you can avoid all conflicts with other Foo functions like this:
namespace ALongNameToType {
struct ALongNameToType {
static void Foo();
};
}
typedef ALongNameToType::ALongNameToType Shortname;
int main() {
Shortname::Foo();
}
namespace myns = ALongNameToType;
It seems that you can't alias a class scope like this:
// second ALongNameToType is a class
namespace myns = ALongNameToType::ALongNameToType;
Maybe you could alias the function it self:
namespace foo
{
class foo
{
public:
static void fun()
{
}
};
}
int main()
{
void (*myfunc)() = foo::foo::fun;
myfunc();
}
using ALongNameToType::ALongNameToType::Foo;
if you just want to use it as Foo().
There are three ways to use using. One is for an entire namespace, one is for particular things in a namespace, and one is for a derived class saying it doesn't want to hide something declared/defined in a base class. You can use the second of those:
using ALongNameToType::ALongNameToType
Unfortunately this isn't working for you (due to the ambiguity of the namespace and the class having the same name). Combining this type of using with a previous answer should get rid of the ambiguity:
namespace alntt = ALongNameToType;
using alntt::ALongNameToType;
But once you've renamed the namespace, you really don't need the using statement (as long as you're comfortable writing the (shortened) namespace every time you use the class:
namespace alntt = ALongNameToType;
alntt::ALongNameToType a;
...