Как инициализировать указатели библиотеки?
Использование Visual Studio 2015 Community Edition.
У меня есть глобальный объект, созданный в библиотеке. Этот объект содержит вектор строк. Этот глобальный объект доступен и используется правильно без проблем, за исключением следующих условий.
Если часть кода приложения, отсутствующая в библиотеке, создает исключение, обработка исключений вызывает этот объект для доступа к вектору строк для целей отчетности.
catch (Exception & e) { dwl::Globals * p = gDwlGlobals; //Test to see if accessing gDwlGlobals this way fixes it. wStringStream s; //For debugging, just to see if the address is same as previous s << p; //quick way to print address to debug output OutputDebugString(s.str().c_str()); const Strings & strings = gDwlGlobals->strings(); //See A. wString str = strings[Strings::Error_Programming]; //See B. ...То
OutputDebugString
дает тот же адрес для глобального, что и глобальный, показанный во время создания экземпляра.At (*A*) - в отладчике глобальный адрес отображается правильно в этой строке, а '
strings
"вектор показывает 79 элементов в нем через выпадающие списки.В (*Б*) - В
strings
вектор теперь пуст! И enum
смещение создает исключение в моем исключении.Какие-нибудь указания?
Что я уже пробовал:
Все, что я могу придумать, кроме исключения библиотечного подхода и проверки того, исправляет ли это решение в одном проекте. (Я думаю, что это исправит его, потому что я не помню, чтобы эта ошибка произошла до разделения его на библиотеку. Но я хотел бы знать, почему это не работает.)
Хорошо, я просто попытался исключить подход lib. Как и предполагалось, ошибка исчезает. Так что проблема, должно быть, в том, что
extern
определения почему-то не совпадают в библиотечном и небиблиотечном коде, Хотя существует только одно истинное неэкстерное определение. Какие-нибудь указатели на синхронизацию указателей lib с основным приложением?
CPallini
Что такое сигнатура метода "strings"?
David O'Neil
const Strings & strings() const { return stringsC; }
David O'Neil
(и я поместил точку останова в деструктор строк, который не срабатывает)
CPallini
А 'stringsC' - это глобальный объект... Ладно, теперь я в растерянности, как и ты.
David O'Neil
Технически это элемент глобального объекта, но разницы быть не должно, тем более что он работает как внебиблиотечный проект:namespace dwl {
class Globals {
private:
Strings stringsC;
public:
const Strings & strings() const { return stringsC; }
};
}
Richard MacCutchan
Это действительно ужасный способ использования объектов. Ваша библиотека должна предоставлять методы для возврата указателя или ссылки на вектор. Обращение к нему непосредственно таким образом неизбежно приведет к проблемам.
David O'Neil
Учитывая решение, которое я только что опубликовал, я был бы признателен за ваши отзывы. Является ли подход, описанный в моем предыдущем ответе вам, плохим для управления самим объектом глобальной библиотеки? Как я уже говорил ранее, я получаю доступ к библиотечному вектору через постоянную ссылку, поэтому я не понимаю, почему вы утверждаете, что это ужасный способ использовать объект, когда я использую его, как вы рекомендуете позже в комментарии.
Спасибо!
Richard MacCutchan
Глобальные ссылки были плохой идеей с 80-х годов (и, вероятно, раньше). Проблема такого подхода заключается в том, что приложение и его библиотека становятся слишком тесно связанными. Библиотека должна предоставлять класс или интерфейс, который предоставляет некоторую информацию в виде возвращаемого значения на основе запросов от приложения. Библиотека гарантирует предоставление этой информации в определенном формате или структуре. Однако внутренне (в библиотеке) этими данными можно управлять различными способами. Единственное, чего я не понимаю, так это зачем вам вообще нужна библиотека, если это статические данные.
David O'Neil
В этом случае приложение и его библиотека действительно так тесно связаны. Это моя оконная обертка: https://www.codeproject.com/Articles/793604/DWinLib-Pretty-WinAPI-Incorporation-да. Я превратил его в библиотеку для обучения и для того, чтобы посмотреть, уменьшится ли время компиляции, когда библиотека будет стабильной. Я мог бы сделать необходимым вызов функции для доступа gDwlGlobals
но с учетом тесной связи я не вижу причин для этого. Если у вас есть еще какие-то соображения по этому поводу, я хотел бы их услышать.