типов подскажите у кого какие лучшие практики с nested namespaces.
Несколько раз сталкивался с такой проблемой:
// foo.h
namespace my { class foo; }
// bar.h
#include "foo.h"
namespace my::internal
{
void bar( foo& ); // << unqualified name. По задумке автора это my::foo
}
// internal/foo.h
namespace my::internal { class foo; }
// baz.cpp
#include "internal/foo.h"
#include "bar.h" // << а вот тут у нас odr-violation и my::internal::bar( foo& ) теперь принимает my::internal::foo
Все прекрасно компилируется, вы получаете разные лэйауты в разных юнитах трансляции для имени foo и просто какуюто кашу в памяти в рантайме, дебажится это плохо, потому что детектится проблема неочевидно, особенно на больших кодовых базах, довольно неприятные баги.
Что делать в таком случае? Всегда использовать полные имена со всеми неймспейсами даже если они в родительском неймспейсе? Это плохо контроллировать, для компилятора это валидно, а переносить поддержку этого на человека и код ревью не выглядит как что-то надежное.
Не использовать nested namespaces?
не писать в nested классы из родителя
А bar сама по себе же не нарушение odr? Тут разные декларации, вот если это метод класса то да
Обсуждают сегодня