Основной урок: Включения обрабатываются до разбора любого C ++.Они обрабатываются прекомпилятором.
Допустим, что A.h
включается до B.h
.Вы получаете что-то вроде этого:
#ifndef A_H
#define A_H
// ----- B.h include -----
#ifndef B_H
#define B_H
#include "A.h" // A_H is defined, so this does nothing
struct B {
int b;
};
void doStuff2 (A a); // Error here
#endif
// ----- B.h include -----
struct A {
int a;
};
void doStuff1 (B b); // Error here
#endif
На этом этапе компилятор C ++ может вступить во владение и начать анализировать вещи.Он попытается выяснить, что это за параметр doStuff2
, но A
еще не определен.Та же логика верна, если идти другим путем.В обоих случаях у вас есть зависимости от типов, которые еще не были определены.
Все это просто означает, что ваши зависимости вышли из строя.Это не проблема с передачей по значению.Ваши типы должны быть определены до ваших методов.Вот и все - см. Пример ниже.
// Example program
#include <iostream>
#include <string>
// data_types.h
struct A
{
int x;
};
struct B
{
int y;
};
using namespace std;
// methods_A.h
void foo(A a)
{
a.x = 3;
cout << "a: " << a.x << endl;
}
// methods_B.h
void bar(B b)
{
b.y = 4;
cout << "b: " << b.y << endl;
}
int main()
{
A first;
B second;
first.x = 0;
second.y = 100;
foo(first);
bar(second);
cout << "A: " << first.x << ", B: " << second.y << endl;
}
Пример вывода
a: 3
b: 4
A: 0, B: 100