将辅助函数移至头文件

时间:2018-08-03 09:03:51

标签: c++ c++14 header-files

一开始我有:

main.cpp

#include "something.h"
#include "util.h"

int main() {
    sth::something();
    utl::little_thing();
}

somehing.h

#ifndef SOMETHING_H
#define SOMETHING_H

namespace sth {

void something();

}
#endif

somehing.cpp

#include "something.h"

#include <string>
#include <iostream>

namespace sth {

void print_me(std::string txt) {
    std::cout << txt << std::endl;
}

void something() {
    std::cout << "this is something" << std::endl;
    print_me("optional");
}
}

util.h

#ifndef UTIL_H
#define UTIL_H

namespace utl {

void little_thing();

}
#endif

util.cpp

#include "util.h"

#include <iostream>
#include <string>

namespace utl {

void little_thing() {
    std::cout << "this is little thing" << std::endl;
}
}

然后我将print_me(std::string txt)sth命名空间中删除会更好。然后放在utl上,在.h文件上声明,在.cpp文件上定义。

那时我懒惰的一面说-最好像以前一样将所有文件都保存在一个文件中。我尝试过:

util.h

#ifndef UTIL_H
#define UTIL_H

#include <string>
#include <iostream>

namespace utl {

void little_thing();

void print_me(std::string txt) {
    std::cout << txt << std::endl;
}
}
#endif

something.cpp

#include "something.h"
#include "util.h"

#include <string>
#include <iostream>

namespace sth {

void something() {
    std::cout << "this is something" << std::endl;
    utl::print_me("optional");
}
}

所以我得到了

c++ -std=gnu++14 -g -Wall -O3  -c -o main.o main.cpp
c++ -std=gnu++14 -g -Wall -O3  -c -o util.o util.cpp
c++ -std=gnu++14 -g -Wall -O3  -c -o something.o something.cpp
c++ main.o util.o something.o  -o main
duplicate symbol __ZN3utl8print_meENSt3__112basic_stringIcNS0_11char_traitsIcEENS0_9allocatorIcEEEE in:
    main.o
    util.o
duplicate symbol __ZN3utl8print_meENSt3__112basic_stringIcNS0_11char_traitsIcEENS0_9allocatorIcEEEE in:
    main.o
    something.o
ld: 2 duplicate symbols for architecture x86_64
clang: error: linker command failed with exit code 1 (use -v to see invocation)
make: *** [main] Error 1

在我看来,util.hmain.cpp中包含something.cpp,所以有重复的符号,对吗?

问题,是否有可能懒惰地将其全部包含在标题中?还是没有办法,必须将比例和定义分开?我不在乎(在这种情况下)将实现隐藏在.cpp中,我只想将其移出sth

1 个答案:

答案 0 :(得分:-1)

也许将print_me的定义下移到util.cpp,而只在util.h文件中声明它。

否则,在每个目标文件中都会得到一个副本,然后链接器会因为它们都具有相同的名称(符号)而感到困惑。