Назначение extern единственное. Мы говорим, что этой переменной нет в данной единице компиляции, но не надо переживать, она есть в другой и компоновщик её подкомпонует.
По факту является extern’ом static-поле класса. Это решение принято Строуструпом по простой причине: определение класса может промелькнуть несколько раз в разных единицах компиляции, а определение переменной должно быть одно на программу.
Если ваш код не работает без extern — это значит, что где-то нашлась глобальная переменная по имени client, и для корректной работы вебмастера потребовалось обращаться к этому нашему клиенту. По факту — очень навороченный способ создать static-поле.
Таким образом, у вас три варианта.
1. Если Ethernet-клиент один на всех вебмастеров, вам нужно static-поле.
// HEADER
class WebMaster {
public:
WebMaster();
bool connect_open();
private:
static EthernetClient client;
}
// CPP
EthernetClient WebMaster::client;
Впрочем, этот вариант крайне маловероятен.
2. Скорее всего, у вас один вебмастер — один клиент и, вероятно, вам нужно обычное нестатическое поле.
class WebMaster {
public:
WebMaster();
bool connect_open();
private:
EthernetClient client;
}
3. Если у нас приходится привязывать мастеров к клиентам, приходится использовать указатели и ссылки. В простейшем виде…
// HEADER
class WebMaster {
public:
WebMaster(EthernetClient& aClient);
bool connect_open();
private:
EthernetClient& client;
}
// CPP
WebMaster::WebMaster(EthernetClient& aClient) : client(aClient) {}
...
EthernetClient client;
WebMaster webmaster(client);