extern versus namespace

Pages: 12
closed account (jvqpDjzh)
I've almost never used the keyword extern, in fact I've never needed it. If you want to use functions from another file, you can put those functions in a namespace, include the file header and declare we are going to use those functions from that namespace. My question is for what we really need the keyword extern (where we can't use a namespace)? Examples are more appreciated.
Thank you.
Last edited on
namespace and extern are not related.

extern is used for the declaration of a global variable. This variable must be defined in a module (cpp) so that it can be found by the linker (otherwise you will get linker errors)
The most common use of extern I see is for global variables. Obviously, a global variable cannot be defined in multiple places, so you'll need to specify with extern that it is defined outside of that particular translation unit. For example:
1
2
3
4
5
6
7
// a.cpp
#include <iostream>
int a;

void doSomething() {
    std::cout << a << '\n';
}

1
2
3
4
5
6
7
8
9
// b.cpp
extern int a; // a is outside of this translation unit
void doSomething(); // we only need to prototype the function

int main() {
    a = 10;
    doSomething();
    return 0;
}

Of course, as a general rule global variables should be avoided, but there are some times where you do need them (or just go crazy from how complicated your constructors and the like need to be to pass it around everywhere - in some projects, some things are meant to be global).
Last edited on
closed account (jvqpDjzh)
Why should you use just 1 global variable? It might be related with something else. You put them all in a namespace without extern.
If you want to use functions from another file, you can put those functions in a namespace
Why would you need a namespace for that
you can put those functions
You mean those function declarations? Violating One Definition Rule will get you non-working program.

Extern keyword has two meaning. First one is specifying static storage duration with external linkage:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
//main.cpp

namespace {
int i = 5;
}

void dothings();

int main()
{
    dothings();
    std::cout << i;
}
//other.cpp;
namespace {
int i = 5;
}
void dothings()
{
    i = 100;
}
5
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
//main.cpp
extern int i;

void dothings();

int main()
{
    dothings();
    std::cout << i;
}
//other.cpp;
extern int i = 5;
void dothings()
{
    i = 100;
}
100


Other meaning is to specify linkage parameters (used in interactio between programs): http://en.cppreference.com/w/cpp/language/language_linkage

You put them all in a namespace without extern.
And you cannot change them from another module by doing that. Extern have limited uses, but that does not means that it is useless. For example standard streams std::cin/std::cout/... are declared extern
Last edited on
See the following files:
http://coliru.stacked-crooked.com/a/73f728c1d0760349 (header)
http://coliru.stacked-crooked.com/a/b0f08f05111f44aa (a.cpp)
http://coliru.stacked-crooked.com/a/17f9ee5ace56f928 (main.cpp)

Especially, look at the main.cpp file to see the multiple definition errors. This is what extern is trying to avoid.
And see the following files too (unamed namespace):
http://coliru.stacked-crooked.com/a/aaa75527e143af18 (header)
http://coliru.stacked-crooked.com/a/686f13a6fde7f8bf (a.cpp)
http://coliru.stacked-crooked.com/a/c5f961a855ec8848 (main.cpp)
Multiple definition errors have dissapeared, but it is not behaving as you probably want.

And these:
http://coliru.stacked-crooked.com/a/d4c1f2420bd8336e (header)
http://coliru.stacked-crooked.com/a/686f13a6fde7f8bf (a.cpp)
http://coliru.stacked-crooked.com/a/a9485e895120264d (main.cpp)
to see how extern is used
closed account (jvqpDjzh)
Violating One Definition Rule will get you non-working program.
I didn't catch what you really mean by this.

This is not working: multiple definitions of ve::a. Where? But I am wondering if this wouldn't be more easy a better:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
//ve.h
#ifndef VE_H
#define VE_H
namespace ve
{
	int a;
	
	void setA(int);
	int  getA();
}
#endif

//ve.cpp
#include "ve.h"
void ve::setA(int x)
{
    ve::a = x;
}

int ve::getA()
{
    return ve::a;
}

//main.cpp
#include "ve.h"
#include <iostream>

int main()
{
	int a = 10;
	
	std::cout << "a from ve: " << ve::a << '\n';
//well the operator :: should be use for something useful
	
	ve::setA(20);
	
	std::cout << "local a: " << a << '\n';
	
	std::cout << "a from ve again: " << ve::getA()<<'\n';
	
	return 0;
}


EDIT: for me extern has no sense and should be deprecated. We could use a namespace similar to a class. Simple extern is old. Or so for what should we use namespacesss? The name says everything!!!!

EDIT: The only thing I like from C++ more than from other languages such as JAVA or C# is that is handles also lower level stuff, such as pointers, otherwise C++ is an old language that tries to imitates the other modern good languages.
Last edited on
> for me extern has no sense and should be deprecated. We could use a namespace similar to a class
¿does your example work?


> This is not working: multiple definitions of ve::a. Where?
$ nm -C ve.o
0000000000000000 B ve::a
0000000000000012 T ve::getA()
0000000000000000 T ve::setA(int)

$ nm -C main.o
0000000000000000 T main
0000000000000000 B ve::a
                 U ve::getA()
                 U ve::setA(int)
                 U std::ostream::operator<<(int)
see how 've::a' is defined in ve.o and in main.o
because you put the definition in a header that is included in those two source files.
I didn't catch what you really mean by this.
Each function, variable, etc. should have only one defunutuion. HAving more is illegal and leads to the error like↓↓↓

multiple definitions of ve::a. Where?
One in ve.cpp, one in main.cpp. You have included it in both so it is defined in both. Read how include works.

Simple extern is old
Tell me, how to implement things like standard streams without using extern.

C++ [...] tries to imitates the other modern good languages.
I am curious, where it imitates other languages? Only things I see is adopting abstract CS idioms.
closed account (jvqpDjzh)
With C++ 11 they have introduced:
1. the keyword override to explicit say that a function is override. This of course have been copied from C#.

2.
Smart pointers
? Therefore we should use garbage collector.

3.
Lambda functions
? It seems they are trying to imitate the inner classes methods of JAVA, which are very useful and more natural than the lambda stupid functions.

4. New for loop? No comment.

5. Many types of char*, including the famous useful
verbatim (raw)
strings ? => C#.

6. final keyboard? => lol
7.
Regular expressions
? => lol
8. decltype? ahah
9. auto? It will introduce more and more confusion (in some cases)

If you know other imitations of other languages constructs, please share with out community.

Another thing, for what should we use struct, if we have class?

Last edited on
closed account (jvqpDjzh)
Here's the intelligent solution:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
//ve.h
#ifndef VE_H
#define VE_H

namespace ve
{
	void setA(int);
	int  getA();
}
#endif

//ve.cpp
#include "ve.h"

namespace ve
{
	int a;
	
	void setA(int x)
	{
	    a = x;
	}
	
	int getA()
	{
	    return a;
	}	
}

#include "ve.h"
#include <iostream>

int main()
{
	int a = 10;
	
	ve::setA(20);
	
	std::cout << "local a: " << a << '\n';
	
	std::cout << "a from ve again: " << ve::getA()<<'\n';
	
	return 0;
}


Better than this just football or p*ssy.

Last edited on
1. It was in Java long before C# so your of course is nonsensual here and proposition to add explicit requirement to override functions is as old as bugs linked with it.

2. Example of RAII which as old as C++ itself. I seen smart pointer in code written in 89 and auto was introduced in C++98. It is just move semantics which allowed to transparently create them.

3. Lambda calculus and anonymous functions are older than computers. It is abstract math idiom. After rise in popularity of them in CS, language was modified to add support of them. It is not copies modern languages, it is following latest tendensies in infrastructure. (In Java lambdas were introduced later than in C++ actually)

4. Yes, it is adopting often requested and useful feature other languages are using.

5. Strings were included in C++ before C# was created.
Many types of char*,
What?

6. final: read override. Proposals were there for very long time

7. Regexps are predates most programming languages. Boost had them from 1998.

8. 9. Template metaprogramming and removal of crutches which were nessesary because of lack of those? Sorry, never heard of that?


Another thing, for what should we use struct
Backward compatibility (and aggregates)


First of all you should remember that C++11 is first major language revision after 1998. And it included all changes for those 13 years.
Second: there is Boost aka demo-version of future changes in standard library aka "standard library 2 de-facto"


EDIT: Now make several compilation modules to be able to chnge single variable

I still do not see implementation of std::cin without extern. I'm waiting. Say it should write in specific file. And if should do so from any cpp. file without errors.
Last edited on
closed account (jvqpDjzh)
Le'ts try to comment your declarations:

1.
1. It was in Java long before C# so your of course is nonsensual here and proposition to add explicit requirement to override functions is as old as bugs linked with it.
? And? What's is the difference? In Java or C#, C++ copied from them. Your statement has only historical importance. I have just the moment, sorry.

2. Example of RAII which as old as C++ itself. I seen smart pointer in code written in 89 and auto was introduced in C++98. It is just move semantics which allowed to transparently create them.
They are retarded.

3. And? Also recursion, etc. Lol, your comments can't answer to my declarations in a imperative mode.

4. lol

5.
What?
1
2
3
4
5
6
7
8
// C++ 03:
char*     a = "string";  

// C++ 11:
char*     a = u8"string";  // to define an UTF-8 string. 
char16_t* b = u"string";   // to define an UTF-16 string. 
char32_t* c = U"string";   // to define an UTF-32 string. 
char*     d = R"string \\"    // to define raw string.  

//these from the information that I receiced.

6.
Proposals were there for very long time
long long long long time.

7. Who gives about boosts? They are not standard, from what I know.

8.
crutches which were nessesary because of lack of those
I admit I don't have much experience with template metaprogramming, but you are talking about what crutches?

9.
Backward compatibility (and aggregates)
Yes, for what? Confusion? Why C++ programmers continue to say to use vector or string classes instead of the C programming constructs? Nonsense.

First of all you should remember that C++11 is first major language revision after 1998. And it included all changes for those 13 years.
Copying all other good languages.

EDIT: Now make several compilation modules to be able to chnge single variable
This is your problem? EDIT: actually, when you have to change a single variable, you probably change also other related things, so you should do it anyway.

I still do not see implementation of std::cin without extern. I'm waiting. Say it should write in specific file. And if should do so from any cpp. file without errors.
And, what does it mean? That it's the best way one should do it? Just obsorve other completely OOP languages.
Last edited on
And, what does it mean? That it's the best way one should do it?
No. I am saying that it is the only way to do it.

This is your problem?
No, this is a requirement. I want to have truly global variable. Accessible from all modules.

Copying all other good languages.
Java and C# has stolen: classes from Simula, garbage collection from Lisp, regexes (most used version) from Perl, inner classes from C++, modules form Pascal, automatic variable type deduction from Fortran, operators from algol and functions from assembly. And their whole syntax from C++. So they should drop these features and instead develop their own unique features.
On a side note, only cars produced by Heneral Motors should use automatic transmission, because they invented it and other companies using it would copy it. Also you should use Roman numerals and whichever measurement system your ansectors used and not copy other useful and de-facto standard library.
Do I understand you correctly?

Copying all other good languages.
Those other languages copied already pending proposals and just implemented it faster :)

Yes, for what?
For one of the main aims of C++.

you are talking about what crutches?
About value_type, iterator_type and other embers typedefs. And if you like to write std::unordered_map<std::basic_string<char32_t>, std::function<std::vector<boost::shared_ptr<resource> >(std::basic_string<char32_t>, int)> >::iterator (real code) you should avoid them

Who gives about boosts?
Every single competent programmer? Ever Standard Comitee members are promoting Boost (or writing it)

these from the information that I receice.
Unicode support added. Adequate people: finally, we waited 20 years fpr that. zwulu: no, there is unicode in other languages! Seriously, what your problem with multibyte characters and Unicode.

lol
What? I am agreeing with you. Total copy of most used type of loop.

They are retarded.
Who? smart pointers? Garbage collectors even more retarded and slow. Also lack of sensible RAII in Java and C# leads to extra work of ensuring that all claimed resources (aside from memory) are released properly.

3. I made a point: how could C++ steal feature that was implemented in Java later? And you pointed to feature in Java which existed in C++ before Java creation.



Main point: All features of computer sciens were invented long ago. They were tested, proved themself useful and were adopted by programming languages. C++ is nonoriously slow to adopt those, so you will see it as copying features as it adopts it later than other languages.
closed account (jvqpDjzh)
No. I am saying that it is the only way to do it.
Maybe for C++.

No, this is a requirement. I want to have truly global variable. Accessible from all modules.
How do other languages (C# and JAVA) solve that?

Copying all other good languages.
I am not saying that languages don't take reference from others to be created or to evolve, I am just saying that C++11 has introduced many constructs and other things from other languages (JAVA and C#) where they are very useful.

For one of the main aims of C++.
Why still insisting with compatibility (with C) and the past, if C++ is better, and can, from what I know, do everything that in C is done, without using C constructs?

Every single competent programmer? Ever Standard Comitee members are promoting Boost (or writing it)
I am not a real programmer, as you know, and I am far from it, unfortunetely. I just think that there are many things in C++ that are useless, like continueing to use the keyword struct. Also the syntax of C++ is becoming a mess, and will get worse, because they are always introducing new things. C# and JAVA are more smart.


Who? smart pointers? Garbage collectors even more retarded and slow. Also lack of sensible RAII in Java and C# leads to extra work of ensuring that all claimed resources (aside from memory) are released properly.
No. Not smart pointers, people that handles the evolution of this fantastic programming language.
I like the idea of smart pointers, don't misunderstand me. I just say that C++ is trying to avoid pointers management, is trying to become JAVA and C# and many other languages.

I made a point: how could C++ steal feature that was implemented in Java later? And you pointed to feature in Java which existed in C++ before Java creation.
C++ is trying to become the other languages, it's trying to evolve, because it's retarded in many things, it wants to provide you to do anything, but it becomes a mess: there are many useless constructs in C++ that should be deprecated and deleted from the language, because they create only confusion, and this is not good if you want to concentrate yourself in the logic of the program:should be as natural as possible to express solutions to problems. In C++, most of the time, you lose much time for taking care about pointers and dynamic memory management, but this is good, if you want to create a performant application, but you can't concentrate yourself to create innovative programs, because you are always fronting the same old problems. C++ is the most powerful, because it is an high level language, but we can also manage low level aspects, but there are many things that should be deleted before continue to introduce new things.
Last edited on
Maybe for C++.
Surprise! languages are different and do work differently. C++ and C# have limited duck typing, Java has ugly imitation achieved through reflection, Perl and Python has full support of it.
Java does not support freestanding functions, Pascal does not support member function, C++ support both.
Go does not have implementation inheritance, using it in Java is discouraged by it author, and if Going Native 2013 convention is of any indication it is not encouraged in C++ too, but C++ makes heavy use of it and it is unlikely to change soon.
Many languages does have neat syntax for lately invented features, C++ syntax is more heavy, because those features were not used in CS when it was created and new features should be added to not break old code.

C++ has its own aims and reasons for most of his syntax. Java has its own share of backward compatibility crasiness.

When in Rome do as Romans do. When you are using programming language, use constructs recommended for this language.
There is saying: you can write in Fortran in any language. Do not do that. Deal with limitations and features of the language you are writing in.
Do not try to write code you will write in Java. Learn what C++ can offer and use this.

C++ include for example does not work like other languages modules. But if you have 15 souce files, you can compile them on 15 different computers (or on one but in different times) and link them together later.
Other languages have other quirks (for example C# programmers tend to always link with most modern version of .NET which is really annoying — Java programs are usually better in that regard)
closed account (jvqpDjzh)
Surprise!
I don't like surprises.

Do not try to write code you will write in Java. Learn what C++ can offer and use this.
Mess. Not productive, but stills the most powerful that I know, for pointers.

Java programs are usually better in that regard
It's not better, it's the best.

One thing I can assure you: I am not a really programmer, and rules are not perfect, and I don't like imperfect rules, but who gives?

Good programming to all the nerds, who have only one purpose and passion in life, unfortunately for you!
It's not better, it's the best.
Yeah. Go for industrial programming. Try to install Java on QNX or MS-DOS. Try to program in Java 5 (latest supported for windows 98)
Try to run Java on 128mb of memory.
Java is good for user-level applications on desktops or not-speed-critical applications on most other personal gadgets. Still I would like to hear about highload systems in Java.

stills the most powerful that I know, for pointers
Let me get it straight: you like C++ for feature you should avoid to use in raw form? It is somehow counterproductive. Do not use C++, use C instead.

Mess. Not productive
Because you cannot use it productively and constantly trying to perform rectal tonsillectomy with it.
Writing Forthran in other languages

I don't like imperfect rules
Nothing is perfect.

Good programming to all the nerds, who have only one purpose and passion in life, unfortunately for you!
Personal insults? Ok, I am out of this topic now.
MiiNiPaa wrote:
so your of course is nonsensual here


I just thought that was funny.

Although, I would agree that most of zwilu's arguments are nonsensical.
Pages: 12